120 lines
3.4 kB
1
defmodule BlogWeb.PythonLive.Index do
2
use BlogWeb, :live_view
3
alias Blog.PythonRunner
4
require Logger
5
6
@python_example """
7
import random
8
9
# Roll some dice
10
dice = [random.randint(1, 6) for _ in range(3)]
11
f"You rolled: {dice} (sum: {sum(dice)})"
12
"""
13
14
@impl true
15
def mount(_params, _session, socket) do
16
# Initialize the Python environment - now returns :ok instead of {:ok, _}
17
python_status = case PythonRunner.init() do
18
:ok -> :available
19
{:error, reason} -> {:unavailable, reason}
20
end
21
22
# Get the hello world result
23
hello_result = if python_status == :available do
24
try do
25
{result, _} = PythonRunner.hello_world()
26
result
27
rescue
28
e ->
29
Logger.error("Error running hello world: #{inspect(e)}")
30
"Error: #{inspect(e)}"
31
end
32
else
33
"Python unavailable"
34
end
35
36
{:ok, assign(socket,
37
code: @python_example,
38
result: "",
39
hello_result: hello_result,
40
python_status: python_status
41
)}
42
end
43
44
@impl true
45
def handle_event("run-code", %{"code" => code}, socket) do
46
result = if socket.assigns.python_status == :available do
47
try do
48
PythonRunner.run_code(code)
49
rescue
50
e ->
51
Logger.error("Error executing Python code: #{inspect(e)}")
52
"Error: #{inspect(e)}"
53
end
54
else
55
"Python is unavailable"
56
end
57
58
Logger.info("Python code execution result: #{inspect(result)}")
59
{:noreply, assign(socket, result: result)}
60
end
61
62
@impl true
63
def render(assigns) do
64
~H"""
65
<div class="container mx-auto p-4">
66
<h1 class="text-2xl font-bold mb-4">Python Integration Demo</h1>
67
68
<div class="mb-6 p-4 rounded bg-gray-100">
69
<h2 class="text-xl font-semibold mb-2">Python Status</h2>
70
<%= if @python_status == :available do %>
71
<div class="text-green-600 font-bold">✅ Python is available</div>
72
<% else %>
73
<div class="text-red-600 font-bold">❌ Python is unavailable</div>
74
<div class="mt-2 p-2 bg-yellow-100 rounded">
75
<p>Reason: <%= inspect(@python_status) %></p>
76
</div>
77
<% end %>
78
</div>
79
80
<div class="mb-6 p-4 rounded bg-gray-100">
81
<h2 class="text-xl font-semibold mb-2">Hello from Python</h2>
82
<div class="p-2 bg-white rounded border">
83
<%= @hello_result %>
84
</div>
85
</div>
86
87
<div class="mb-6">
88
<h2 class="text-xl font-semibold mb-2">Try Python Code</h2>
89
<form phx-submit="run-code">
90
<div class="mb-4">
91
<textarea
92
name="code"
93
rows="10"
94
class="w-full p-2 border rounded font-mono"
95
placeholder="Enter Python code here"
96
disabled={@python_status != :available}
97
><%= @code %></textarea>
98
</div>
99
<button
100
type="submit"
101
class="bg-blue-500 hover:bg-blue-700 text-white font-bold py-2 px-4 rounded"
102
disabled={@python_status != :available}
103
>
104
Run Code
105
</button>
106
</form>
107
</div>
108
109
<%= if @result != "" do %>
110
<div class="mt-4">
111
<h3 class="text-lg font-semibold mb-2">Result</h3>
112
<div class="p-4 bg-gray-100 rounded font-mono whitespace-pre-wrap">
113
<%= @result %>
114
</div>
115
</div>
116
<% end %>
117
</div>
118
"""
119
end
120
end
121