Прежде чем перейти к Flask и поделиться, давайте посмотрим, что вы хотите сделать с чисто программной стороны. Вы хотите использовать переменную в двух функциях.
Есть несколько способов сделать это. Один из них — использовать globals, который вы пробовали и обнаружили, что это не решение. Некоторые другие способы, которые приходят мне на ум:
- Инкапсуляция связанных функций с помощью класса
- Передача общей информации в качестве аргумента другой функции
- Поддержание регистратора для хранения и извлечения по желанию
1. Инкапсуляция с использованием классов
Поскольку Flask спроектирован так, чтобы быть простым и использует функции как первоклассные граждане для создания представлений, инкапсуляция с использованием классов не дала бы этой цели. Правильная альтернатива — использовать Flask Blueprints для группировки функций, которые будут иметь общие данные. Это означало бы использование глобальных переменных в модуле чертежа, и мы столкнулись бы с той же проблемой, что и с globals.
2. Передача значения в качестве аргумента
Это прямой способ поделиться ценностями в обычной ситуации. В этом случае, когда каждая функция привязана к URL-адресу в качестве представления, это может работать или не работать в зависимости от возможности отслеживания вашего объекта процесса x. Предположим, что у вас есть функция get_process(process_id), тогда вы могли бы сделать что-то вроде этого:
@app.route("/process")
def process():
x = process_obj()
return render_template('result.html', x=x)
В вашем шаблоне отобразите ссылку как:
<a href="{% url_for('kill', id=x.id) %}">Kill Process</a>
Затем получите значение в своем представлении kill следующим образом:
@app.route("/kill")
def kill():
id = request.args.get("id", None)
if not id:
abort(400)
x = get_process(id)
x.close()
Примечание. Если этот процесс, о котором вы говорите в псевдокоде, управляется диспетчером задач, таким как Celery или Python-RQ, то вышеприведенное решение должно работать, поскольку они поставляются со способами получения заданий на основе их идентификатора. .
3. Ведение регистратора
Если вы не используете диспетчер задач и самостоятельно выполняете что-то вроде многопроцессорной обработки или какой-либо формы фонового процесса aysnc, в этой системе должен быть регистратор, который позволит вам отслеживать и извлекать процессы, которые вы запускаете.
Я бы посоветовал не делать этого и выбрать хорошо протестированную библиотеку, такую как Celery, Python RQ, Huey и т. д., чтобы сделать это за вас.
Обновление. Чтобы создать регистратор ресурсов, создайте класс с одноэлементным шаблоном, доступ к которому можно получить через приложение. Поскольку вы используете Flask, я бы посоветовал создать его как расширение Flask, чтобы вы могли поделиться им вместе с приложением и при необходимости использовать контекст приложения.
Следующий псевдокод должен помочь вам:
# import your necessary ssh library objects if required
from flask import current_app, _app_ctx_stack
class MyObjectRegistrar(object):
def __init__(self, app=None):
self.app = app
self.my_objects = {}
if app is not None:
self.init_app(app)
def init_app(self, app):
# load any config into your registrar from the app config if necessary
def add(self, id, obj):
self.my_objects[id] = obj
def get(self, id):
return self.my_objects.get(id, None)
def remove(self, id):
del self.my_objects[id]
С указанным выше регистратором, загруженным как расширение Flask:
from flask import Flask
from my_registrar import MyObjectRegistrar
app = Flask(__name__)
registrar = MyObjectRegistrar(app)
Это даст вам объект регистратора, который вы можете использовать в своих представлениях, например:
@app.route("/process")
def process():
obj = process_obj()
registrar.add("some-unique-id", obj)
return render_template("results.html", id="some-unique-id")
@app.route("/kill")
def kill():
id = request.args.get("id")
x = registrar.get(id)
x.close()
registrar.remove(id)
return render_template("killed.html")
Примечание. Это не обязательно должно быть расширение Flask. Если вы не видите смысла в наличии объекта Flask App, вы можете просто создать одноэлементный класс в обычном модуле Python.
person
Arunmozhi
schedule
20.11.2019