জ্যাঙ্গো প্রকল্পে আমার সিগন্যাল.পি ফাইল রাখার সঠিক জায়গা


88

জ্যাঙ্গোর যে ডকুমেন্টেশন আমি পড়ছিলাম তার উপর ভিত্তি করে, মনে হচ্ছে signals.pyঅ্যাপ ফোল্ডারে শুরু করা ভাল জায়গা, তবে আমি যে সমস্যার মুখোমুখি হচ্ছি তা হ'ল আমি যখন সিগন্যাল তৈরি pre_saveকরি এবং আমি ক্লাসটি মডেল থেকে আমদানির চেষ্টা করি তখন এটির সাথে দ্বন্দ্ব হয় importআমার মডেল

# models.py

from django.contrib.auth.models import User
from django.db import models
from django.utils.translation import gettext as _
from signals import *

class Comm_Queue(CommunicatorAbstract):
    queue_statuses = (
        ('P', _('Pending')),
        ('S', _('Sent')),
        ('E', _('Error')),
        ('R', _('Rejected')),
    )
    status          = models.CharField(max_length=10, db_index=True, default='P')
    is_html         = models.BooleanField(default=False)
    language        = models.CharField(max_length=6, choices=settings.LANGUAGES)
    sender_email    = models.EmailField()
    recipient_email = models.EmailField()
    subject         = models.CharField(max_length=100)
    content         = models.TextField()

# signals.py

from django.conf import settings
from django.db.models.signals import pre_save
from django.dispatch import receiver
from models import Comm_Queue

@receiver(pre_save, sender=Comm_Queue)
def get_sender_email_from_settings(sender, **kwargs):
    obj=kwargs['instance']
    if not obj.sender_email:
        obj.sender_email='%s' % settings.ADMINS[0][1]

এই কোডটি চলবে না কারণ আমি Comm_Queueভিতরে আমদানি signals.pyকরি এবং ভিতরে সিগন্যালগুলিও আমদানি করি models.py

আমি কীভাবে এই সমস্যাটি আসতে পারি সে সম্পর্কে কেউ পরামর্শ দিতে পারেন?

শ্রদ্ধা


উত্তর:


65

জাজানো <1.7 এর জন্য মূল উত্তর

আপনি signals.pyঅ্যাপ্লিকেশনটির __init__.pyফাইলটিতে আমদানি করে সংকেতগুলি নিবন্ধভুক্ত করতে পারেন :

# __init__.py
import signals

এই আমদানি অনুমতি দেবে models.pyথেকে signals.pyবিজ্ঞপ্তি আমদানি ত্রুটি ছাড়া।

এই পদ্ধতির সাথে একটি সমস্যা হ'ল আপনি যদি কভারেজ.পি ব্যবহার করছেন তবে এটি কভারেজের ফলাফলগুলিকে মিস করবে।

সম্পর্কিত আলোচনা

সম্পাদনা করুন: জাঙ্গো> = 1.7 এর জন্য:

যেহেতু অ্যাপকনফিগ চালু হয়েছিল, তাই সিগন্যাল আমদানির প্রস্তাবিত উপায়টি তার init()কার্যক্রমে রয়েছে। দেখুন এরিক মার্কোস 'উত্তর আরো বিস্তারিত জানার জন্য।


6
জ্যাঙ্গো ১.৯-এ সংকেত ব্যবহার করে নীচের পদ্ধতিটি ব্যবহার করুন (জ্যাঙ্গো দ্বারা পুনঃতফসিল)। এই পদ্ধতিটি দেওয়ার কাজ করে নাAppRegistryNotReady("Apps aren't loaded yet.")
s0nskar

4
: এরিক মার্কোস তার উত্তর গৃহীত উত্তর হওয়া উচিত stackoverflow.com/a/21612050/3202958 জ্যাঙ্গো> = 1.7 থেকে, অ্যাপ্লিকেশন কনফিগ ব্যবহার
Nrzonline

4
রাজি। আমি জ্যাঙ্গো 1.7+ এরিক মার্কোসের জবাবের দিকে ইঙ্গিত করার উত্তরটি সম্পাদনা করব
yprez

197

আপনি যদি জ্যাঙ্গো <= 1.6 ব্যবহার করছেন তবে আমি কমাগাটোস সমাধানের পরামর্শ দেব: কেবলমাত্র আপনার মডেলগুলির মডিউল শেষে আপনার সিগন্যালগুলি আমদানি করুন।

জ্যাঙ্গোর ভবিষ্যতের সংস্করণগুলির জন্য (> = 1.7), প্রস্তাবিত উপায় হ'ল আপনার অ্যাপ্লিকেশনটির কনফিগার রেডি () ফাংশনে আপনার সিগন্যাল মডিউল আমদানি করা :

my_app/apps.py

from django.apps import AppConfig

class MyAppConfig(AppConfig):
    name = 'my_app'

    def ready(self):
        import my_app.signals

my_app/__init__.py

default_app_config = 'my_app.apps.MyAppConfig'

7
তারা ১.7 ডকুমেন্টেশনে আরও উল্লেখ করেছেন যে কখনও কখনও প্রস্তুতকে একাধিক বার বলা যেতে পারে এবং তাই সদৃশ সংকেতগুলি এড়াতে আপনার সংকেত সংযোগকারী কলটিতে একটি অনন্য পরিচয়কারী সংযুক্ত করুন: অনুরোধ_ফিনিশডকনেক্ট (আমার_ক্যালব্যাক, প্রেরণ_উইড = "আমার_উনিক_ফিকেশন") যেখানে ডিসপ্যাচ_ইউড সাধারণত স্ট্রিং হয় তবে যে কোনও হ্যাশেবল অবজেক্ট হতে পারে। docs.djangoproject.com/en/1.7/topics/signals/…
এমেকা

13
এটি গ্রহণযোগ্য উত্তর হওয়া উচিত! উউসগি ব্যবহার করে স্থাপন করার সময় উপরে গৃহীত উত্তর একটি ত্রুটি ছুড়ে ফেলে
প্যাট্রিক

4
এইচএম, জ্যাঙ্গো 2 নিয়ে আমার জন্য কাজ করে না i আমি যদি সরাসরি মডেল তৈরি করে আমদানি করি - ঠিক আছে। আমি যদি সংকেতগুলিতে মডেল আমদানি করি এবং প্রস্তুত সংকেতগুলি আমদানি করি তবে আমি একটি ত্রুটি পেয়ে যাচ্ছি doesn't declare an explicit app_label..
আলদারুন্ড

@ অ্যালাদারুন আপনি INSTALLED_APPS এর মধ্যে 'my_app.apps.MyappConfig' রাখার চেষ্টা করতে পারেন।
রামিল আগলিয়াউদ্দিনভ

26

আপনার সমস্যা সমাধানের জন্য আপনাকে কেবলমাত্র মডেল সংজ্ঞা অনুসারে সিগন্যালস.পি। আমদানি করতে হবে। এখানেই শেষ.


4
এটি এখন পর্যন্ত সবচেয়ে সহজ এবং আমার কোনও ধারণা ছিল না এটি চক্রীয় নির্ভরতা ছাড়া কাজ করবে। ধন্যবাদ!
ব্র্যাডেম

4
উজ্জ্বল। আমার উত্তর চেয়ে ভাল এই মত। যদিও আমি সত্যিই বুঝতে পারি না কীভাবে এটি একটি বিজ্ঞপ্তি আমদানির কারণ নয় ...
ইপ্রিজ

সলিউডে সক্রিয় অটোপেইপ 8 প্লাগইন নিয়ে সমাধান কাজ করে না।
রামুসাস

5

আমি সিগন্যালগুলি.পি ফাইলটিতেও রেখেছি এবং এই কোড স্নিপেটও রয়েছে যা সমস্ত সিগন্যাল লোড করে:

# import this in url.py file !

import logging

from importlib import import_module

from django.conf import settings

logger = logging.getLogger(__name__)

signal_modules = {}

for app in settings.INSTALLED_APPS:
    signals_module = '%s.signals' % app
    try:
        logger.debug('loading "%s" ..' % signals_module)
        signal_modules[app] = import_module(signals_module)
    except ImportError as e:
        logger.warning(
            'failed to import "%s", reason: %s' % (signals_module, str(e)))

এটি প্রকল্পের জন্য, আমি অ্যাপ্লিকেশন পর্যায়ে এটি কাজ করে কিনা তা নিশ্চিত নই।


এটি এখন পর্যন্ত আমার প্রিয় সমাধান হিসাবে এটি অন্যান্য প্যাটার্নগুলির সাথে ফিট করে (যেমন টাস্কপিপি)
aloreলোর

4
এটির সাথে একটি সমস্যা পাওয়া গেছে, আপনি যদি শেলটি শুরু করেন তবে urls.py আমদানি হয় না এবং আপনার সংকেতগুলি সংযুক্ত করা হয় না
aloreলোর

হ্যাঁ, আমার উত্তরটি এক ধরণের পুরানো, এটি দেখে মনে হয় যে আজকাল ডিজেঙ্গোর অ্যাপকনফিগ ক্লাস রয়েছে। গতবার আমি জাঙ্গো ব্যবহার করেছি এটির সংস্করণ 1.3। আশেপাশে তদন্ত করার পরামর্শ দিচ্ছি।
আইসবা

4
আমরা এখনও
১. are

5

পুরানো জ্যাঙ্গো সংস্করণগুলিতে সিগন্যালগুলি লাগানো ভাল হতে পারে __init__.pyবা সম্ভবত models.py(যদিও শেষের দিকে মডেলগুলি আমার স্বাদের জন্য বড় আকারের হবে)।

জ্যাঙ্গো ১.৯ এর সাহায্যে, আমার মনে হয়, কোনও signals.pyফাইলে সিগন্যাল স্থাপন করা এবং সেগুলি দিয়ে আমদানি করা apps.py, যেখানে তারা মডেলটি লোড করার পরে লোড হতে চলেছে।

apps.py:

from django.apps import AppConfig


class PollsConfig(AppConfig):
    name = 'polls'

    def ready(self):
        from . import signals  # NOQA

এছাড়াও আপনি আপনার সংকেত বিভক্ত করা যেতে পারে signals.pyএবং handlers.pyআপনার মডেল নামে অন্য কোন ফোল্ডারে signalsপাশাপাশি, কিন্তু আমার জন্য যে শুধু ইঞ্জিনিয়ারিং শেষ হয়ে গেছে। সিগন্যাল স্থাপনের দিকে একবার নজর দিন


3

আমি অনুমান করছি যে আপনি এটি করছেন তাই আপনার সংকেতগুলি নিবন্ধিত হয়েছে, যাতে সেগুলি কোথাও খুঁজে পাওয়া যায়। আমি সাধারণত আমার সিগন্যালগুলি একটি মডেল.পাই ফাইলে রাখি ly


হ্যাঁ আমি যখন মডেল ফাইলের অভ্যন্তরে সিগন্যালটি স্থানান্তর করি তখন এটি সমস্যার সমাধান করে। তবে আমার মডেল.পি ফাইলটি সমস্ত শ্রেণি, পরিচালক এবং মডেল বিধিগুলির সাথে বেশ বড়।
মো জে মুঘরবী

4
পরিচালকরা আমার অভিজ্ঞতার বাইরে আসতে কিছুটা সহজলভ্য। ম্যানেজার.পি.পি.
ইস্যাক কেলি

3

এটি কেবল তখনই প্রযোজ্য যদি আপনার কোনও পৃথক signals.pyফাইলে আপনার সিগন্যাল থাকে

@ এরিকমার্কোসের উত্তরের সাথে পুরোপুরি একমত হলেও এটি উল্লেখ করা উচিত যে জ্যাঙ্গো ডকস স্পষ্টভাবে ডিফল্ট_অ্যাপ_কনফিগ ভেরিয়েবলটি ব্যবহার না করার পরামর্শ দেয় (যদিও এটি ভুল না)। বর্তমান সংস্করণগুলির জন্য, সঠিক উপায়টি হ'ল:

my_app / apps.py

from django.apps import AppConfig

class MyAppConfig(AppConfig):
    name = 'my_app'

    def ready(self):
        import my_app.signals

সেটিংস.পি

(নিশ্চিত হয়ে নিন যে ইনস্টলড অ্যাপ্লিকেশনগুলিতে কেবল আপনার অ্যাপের নাম নেই তবে পরিবর্তে আপনার অ্যাপকনফাইগের আপেক্ষিক পাথ রয়েছে)

INSTALLED_APPS = [
    'my_app.apps.MyAppConfig',
    # ...
]

1

বিকল্পটি হ'ল কলব্যাক ফাংশনগুলি থেকে আমদানি করা এবং এগুলিতে signals.pyসংযোগ স্থাপন করুন models.py:

সংকেত.পি

def pre_save_callback_function(sender, instance, **kwargs):
    # Do stuff here

মডেল.পি

# Your imports here
from django.db.models.signals import pre_save
from yourapp.signals import pre_save_callback_function

class YourModel:
    # Model stuff here
pre_save.connect(pre_save_callback_function, sender=YourModel)

গীত: আমদানি হচ্ছে YourModelমধ্যে signals.pyএকটি পুনরাবৃত্তির তৈরি করবে; senderপরিবর্তে ব্যবহার করুন।

পিএস 2: কলব্যাক ফাংশনে ইনস্ট্যান্সটি আবার সংরক্ষণ করা পুনরাবৃত্তি তৈরি করবে। আপনি .saveএটি নিয়ন্ত্রণ করতে পদ্ধতিতে একটি নিয়ন্ত্রণ যুক্তি করতে পারেন ।

আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.