خطأ أثناء بناء أحدث إصدار

مرحباً. أواجه الخطأ التالي عند تشغيل ./installer rebuild web_only على أحدث إصدارات Discourse.

fs.js:114
    throw err;
    ^

Error: ENOENT: no such file or directory, open 'root='/assets',url='/assets/vendor-4681e47c140b5a5bea2bfb1fec89365858288a8ea0c21979c0167ad9b570ee3d.js.map''
    at Object.openSync (fs.js:438:3)
    at Object.writeFileSync (fs.js:1189:35)
    at done (/usr/lib/node_modules/uglify-js/bin/uglifyjs:516:20)
    at cb (/usr/lib/node_modules/uglify-js/bin/uglifyjs:324:39)
    at /usr/lib/node_modules/uglify-js/bin/uglifyjs:391:9
    at FSReqWrap.readFileAfterClose [as oncomplete] (internal/fs/read_file_context.js:53:3)
rake aborted!
Errno::ENOENT: No such file or directory @ rb_file_s_size - /var/www/discourse/public/assets/vendor-4681e47c140b5a5bea2bfb1fec89365858288a8ea0c21979c0167ad9b570ee3d.js
/var/www/discourse/lib/tasks/assets.rake:268:in `size'
/var/www/discourse/lib/tasks/assets.rake:268:in `block (4 levels) in <top (required)>'
/var/www/discourse/lib/tasks/assets.rake:159:in `block in concurrent?'
/var/www/discourse/lib/tasks/assets.rake:259:in `block (3 levels) in <top (required)>'
/var/www/discourse/lib/tasks/assets.rake:250:in `each'
/var/www/discourse/lib/tasks/assets.rake:250:in `block (2 levels) in <top (required)>'
/var/www/discourse/lib/tasks/assets.rake:159:in `concurrent?'
/var/www/discourse/lib/tasks/assets.rake:247:in `block in <top (required)>'
/var/www/discourse/vendor/bundle/ruby/2.6.0/gems/rake-13.0.1/exe/rake:27:in `<top (required)>'
/usr/local/bin/bundle:23:in `load'
/usr/local/bin/bundle:23:in `<main>'
Tasks: TOP => assets:precompile
(See full trace by running task with --trace)
I, [2019-12-11T22:53:15.806396 #18]  INFO -- : Downloading MaxMindDB...
Compressing Javascript and Generating Source Maps



FAILED
--------------------
Pups::ExecError: cd /var/www/discourse && su discourse -c 'bundle exec rake assets:precompile' failed with return #<Process::Status: pid 17151 exit 1>
Location of failure: /pups/lib/pups/exec_command.rb:112:in `spawn'
exec failed with the params {"cd"=>"$home", "hook"=>"assets_precompile", "cmd"=>["su discourse -c 'bundle exec rake assets:precompile'"]}
f565d457b97d7ff12a258b03a456563a5a0e928c707c70e194ef88ba170aaf3a
** FAILED TO BOOTSTRAP ** please scroll up and look for earlier error messages, there may be more than one

لقد قمت بتعطيل جميع الإضافات، لكن المشكلة ما زالت قائمة. هل يمكن لأي شخص توضيح سبب هذا الخطأ؟

لقد رأينا هذا من قبل في مكان آخر.

هل يمكنك تجربة الأمر التالي:

./launcher cleanup
git pull
./launcher rebuild app

إذا لم ينجح ذلك، جرب حذف جميع الحاويات على الجهاز وجميع الصور.

شكرًا على الرد السريع @sam. سأجرب ذلك.

سؤال سريع. أفترض أن أمر “git pull” يقوم بسحب أحدث إصدار من discourse-docker، أليس كذلك؟

بشكل عام، هل من الضروري ترقية discourse-docker وdiscourse في نفس الوقت؟

حاليًا، لا أتحكم في discourse-docker عبر git. بدلاً من ذلك، أقوم بتحميل إصدار محدد من discourse-docker (كملف Zip) عند إعداد الخادم، وأربط إصدار discourse بـ commit محدد أثناء نشره.

السبب في قيامي بذلك هو محاولة جعل البناء قابلًا للتكرار؛ أي أن تشغيل نفس الأمر مع نفس الإعدادات + المصدر في وقتين مختلفين يجب أن ينتج نفس الملف الناتج. بشكل عام، هذه فكرة جيدة وقد أنقذتني من العديد من الكوابيس التشغيلية مع برامج أخرى على مر السنين :wink: وذلك لأنها تمنحك القدرة على التراجع إلى إعداد معروف بأنه يعمل بشكل جيد.

ومع ذلك، أعتقد أنني أجدف ضد التيار هنا مع discourse، لأنه يبدو أنه يريد سحب أحدث إصدارات أجزاء مختلفة من البرامج أثناء البناء. بدأت أتساءل عما إذا كانت محاولاتي لجعل البناء قابلًا للتكرار تضر بي فعليًا؟

كلماتك صحيحة تمامًا؛ لقد دخلت في حالة غير قابلة للدعم بنسبة 100% مع هذا التلاعب :flushed_face:

نوصي بسحب أحدث إصدار من Git في أقرب وقت ممكن.

صور Docker القديمة لـ Discourse Base غير متوافقة مع الإصدار الحالي من Discourse، بالإضافة إلى أنها تفتقر إلى العديد من التحديثات الأمنية.

شكرًا لك يا @sam. لقد قمت بذلك وأستطيع الآن بناء الإصدار الجديد. لحسن الحظ، كان كل هذا في النسخة التجريبية (beta) لذا لم يحدث أي ضرر :slight_smile: لكنني لست متأكدًا من أن الرغبة في بناء قابل للتكرار تُعد “حيلة برمجية” :thinking:

ما أحاول تحقيقه هنا هو القدرة على التراجع إلى إصدار معروف أنه يعمل بشكل صحيح. لنفترض أنني شغلت الأمر ./launcher rebuild app في الوقت t1 وعمل discourse بنجاح. ثم شغلت الأمر نفسه في الوقت t2 وحدث خطأ ما. كيف يمكنني إعادة البرنامج إلى الإصدار السابق؟ أعتقد أنني أستطيع تقبّل حقيقة أن البناء غير قابل للتكرار إذا كان بإمكاني التراجع إلى حالة معروفة بأنها تعمل. وبما أن الـ launcher قد بنى بالفعل صورة Docker عاملة في الوقت t1، فهل من الممكن إخبار الـ launcher باستخدام صورة محددة بدلاً من الصورة السيئة التي تم بناؤها في الوقت t2؟

أي أفكار؟

آسف على الخروج قليلاً عن الموضوع هنا، يمكنني إعادة النشر إذا رغبت في ذلك.

إذا كنت ترغب في بناء قابل للتكرار، فيجب أن تربط إصدار Discourse المحدد برابط SHA معين عبر إعدادات الحاوية الخاصة بك، بالإضافة إلى كل إضافة.

وهذا يعني أنك ستتوقف عن تلقي التحديثات والإصلاحات لـ Discourse، والإصلاحات الأمنية لصورة Docker وما إلى ذلك، لكن البناء سيكون قابلاً للتكرار إلى حد كبير.

قد تحتاج أيضًا إلى تعديل القوالب لتجميد العناصر وعدم تلقي أي إصلاحات أمنية لاعتمادات apt.

حسنًا، لقد قمت بالفعل بتثبيت إصدار discourse عند نقطة commit محددة، ويمكنني فعل الشيء نفسه مع الإضافات. لكن إذا لم أقوم بتثبيت discourse-docker أيضًا، ألا سيؤدي ذلك إلى حالة يتم فيها تحديث discourse-base في كل عملية بناء بينما لا يتم تحديث discourse؟ ألا سيؤدي ذلك ببساطة إلى عدم توافق مماثل ولكن بالاتجاه المعاكس (لأن discourse-base يتقدم على discourse)؟

أنا مشوش، كيف ظهر هذا الخطأ إذا كان discourse مثبتًا على إصدار قديم؟

إذا كان NGINX يحتوي على ثغرة أمنية حرجة، هل تريد إصلاحها؟

ظهر الخطأ عندما قمت بنقل الإصدار المثبت من Discourse من 2.4.0.beta2 إلى 2.4.0beta8

بالطبع، أود إصلاح الثغرات الأمنية الحرجة في أنظمة البرمجيات التابعة عند تشغيل بناء جديد! يبدو ذلك رائعًا!

ومع ذلك، أود أيضًا أن أتمكن من التراجع في حال كانت النسخة الجديدة معطلة :slight_smile:

دعني أعطي مثالًا ملموسًا:

لنفترض أن تكويني في الحالة الحالية:

discourse: 2.4.0beta2 (مثبت في ملف web_only.yml)

أقوم بتشغيل ./launcher rebuild web_only وجميع الأمور تعمل بشكل صحيح.

الآن أصبح نظامي في هذه الحالة:

discourse: 2.4.0beta2
discourse-docker: LATEST-AT-TIME-T1

الآن أقوم بتغيير التكوين إلى هذه الحالة:

discourse: 2.4.0beta8 (مثبت في ملف web_only.yml)

أقوم بتشغيل ./launcher rebuild web_only ويحدث خلل ما.

أصبح نظامي الآن في هذه الحالة:

discourse: 2.4.0beta8
discourse-docker: LATEST-AT-TIME-T2

الآن أريد العودة إلى النسخة السابقة لاستعادة العمل بشكل صحيح. لذا أقوم بتغيير الإصدار المثبت من Discourse إلى 2.4.0beta2 وأعيد البناء. لكن عند تشغيل ./launcher rebuild web_only، يصبح النظام في هذه الحالة:

discourse: 2.4.0beta2
discourse-docker: LATEST-AT-TIME-T2

على الرغم من أن الإصدار المثبت من Discourse هو نفسه، فإن إصدار discourse-base (والبقية من discourse-docker، والقوالب، و./launcher نفسه، إلخ) سيكون مختلفًا الآن، لذا لن أعود إلى حالة معروفة بأنها سليمة، وأقلق من أن البناء قد يفشل تمامًا.

أعتذر إذا كنت أبدو غبيًا هنا، كل ما أريده هو القدرة على العودة إلى وضع آمن في حال وجود مشاكل أثناء التحديث. ربما إعادة تشغيل ./launcher rebuild web_only ليست الطريقة الصحيحة للتراجع هنا؟ بالنسبة للأنظمة الأخرى التي أقوم بنشرها، سأقوم ببساطة بإعادة نشر صورة Docker سابقة؟ هل هناك طريقة لإخبار الـ launcher بفعل ذلك؟

نعم، يجب عليك إعادة النظر في عملية العمل لديك. عمليات ترحيل قاعدة البيانات لدينا غير قابلة للعكس.

إذا كنت ترغب في تجربة الترقية دون الالتزام، فيجب أن تعمل في بيئة تجريبية معزولة.

نعم، أفهم أن التراجع عن هجرة قاعدة بيانات أمر صعب. من الواضح أن Discourse لم يُصمم مع وضع استراتيجية إدارة الإصدارات والنشر الخاصة بي في الاعتبار. يجب أن أتوقف عن السباحة ضد التيار هنا.

لدي بيئة تجريبية، لذا سأتخلى عن أي أفكار تتعلق بالبناء والنشر القابل للتكرار، وسأختبر في البيئة التجريبية ثم أعقد أصابعي وأصابع قدمي عند الانتقال إلى بيئة الإنتاج.

شكرًا لمساعدتك @sam