1st gen Node.js ফাংশনগুলিকে 2nd gen-এ আপগ্রেড করুন৷

এই নির্দেশিকায় দেওয়া নির্দেশাবলী ব্যবহার করে প্রথম প্রজন্মের ফাংশন ব্যবহারকারী অ্যাপগুলিকে দ্বিতীয় প্রজন্মে স্থানান্তরিত করার কথা বিবেচনা করা উচিত। দ্বিতীয় প্রজন্মের ফাংশনগুলি আরও ভাল কর্মক্ষমতা, আরও ভাল কনফিগারেশন, আরও ভাল পর্যবেক্ষণ এবং আরও অনেক কিছু প্রদানের জন্য ক্লাউড রান ব্যবহার করে।

এই পৃষ্ঠার উদাহরণগুলি ধরে নিচ্ছে যে আপনি CommonJS মডিউল ( require style imports) সহ JavaScript ব্যবহার করছেন, কিন্তু একই নীতি ESM ( import … from style imports) এবং TypeScript সহ JavaScript এর ক্ষেত্রেও প্রযোজ্য।

মাইগ্রেশন প্রক্রিয়া

প্রথম জেনারেশন এবং দ্বিতীয় জেনারেশন ফাংশন একই ফাইলে পাশাপাশি থাকতে পারে। এটি আপনাকে প্রস্তুত থাকাকালীন টুকরো টুকরো করে সহজেই স্থানান্তর করতে সাহায্য করবে। আমরা পরামর্শ দিচ্ছি যে একবারে একটি ফাংশন স্থানান্তর করুন, এগিয়ে যাওয়ার আগে পরীক্ষা এবং যাচাইকরণ করুন।

Firebase CLI এবং firebase-function এর সংস্করণগুলি যাচাই করুন

নিশ্চিত করুন যে আপনি কমপক্ষে Firebase CLI সংস্করণ 12.00 এবং firebase-functions সংস্করণ 4.3.0 ব্যবহার করছেন। যেকোনো নতুন সংস্করণ 2nd gen এবং 1st gen উভয়কেই সমর্থন করবে।

আমদানি আপডেট করুন

firebase-functions SDK-তে v2 সাবপ্যাকেজ থেকে দ্বিতীয় প্রজন্মের ফাংশন আমদানি করা হয়। এই ভিন্ন আমদানি পথটিই ফায়ারবেস CLI-এর জন্য প্রয়োজনীয় যা আপনার ফাংশন কোডকে প্রথম বা দ্বিতীয় প্রজন্মের ফাংশন হিসেবে স্থাপন করবে কিনা তা নির্ধারণ করে।

v2 সাবপ্যাকেজটি মডুলার, এবং আমরা শুধুমাত্র আপনার প্রয়োজনীয় নির্দিষ্ট মডিউলটি আমদানি করার পরামর্শ দিচ্ছি।

আগে: ১ম প্রজন্ম

const functions = require("firebase-functions/v1");

পরে: দ্বিতীয় প্রজন্ম

// explicitly import each trigger
const {onRequest} = require("firebase-functions/v2/https");
const {onDocumentCreated} = require("firebase-functions/v2/firestore");

ট্রিগার সংজ্ঞা আপডেট করুন

যেহেতু দ্বিতীয় প্রজন্মের SDK মডুলার আমদানির পক্ষে, তাই পূর্ববর্তী ধাপ থেকে পরিবর্তিত আমদানি প্রতিফলিত করার জন্য ট্রিগার সংজ্ঞা আপডেট করুন।

কিছু ট্রিগারের জন্য কলব্যাকে পাঠানো আর্গুমেন্টগুলি পরিবর্তিত হয়েছে। এই উদাহরণে, মনে রাখবেন যে onDocumentCreated কলব্যাকের আর্গুমেন্টগুলিকে একটি একক event অবজেক্টে একত্রিত করা হয়েছে। অতিরিক্তভাবে, কিছু ট্রিগারে সুবিধাজনক নতুন কনফিগারেশন বৈশিষ্ট্য রয়েছে, যেমন onRequest ট্রিগারের cors বিকল্প।

আগে: ১ম প্রজন্ম

const functions = require("firebase-functions/v1");

exports.date = functions.https.onRequest((req, res) => {
  // ...
});

exports.uppercase = functions.firestore
  .document("my-collection/{docId}")
  .onCreate((change, context) => {
    // ...
  });

পরে: দ্বিতীয় প্রজন্ম

const {onRequest} = require("firebase-functions/v2/https");
const {onDocumentCreated} = require("firebase-functions/v2/firestore");

exports.date = onRequest({cors: true}, (req, res) => {
  // ...
});

exports.uppercase = onDocumentCreated("my-collection/{docId}", (event) => {
  /* ... */
});

প্যারামিটারাইজড কনফিগারেশন ব্যবহার করুন

দ্বিতীয় প্রজন্মের ফাংশনগুলি functions.config এর জন্য সমর্থন বাদ দেয়, যাতে আপনার কোডবেসের ভিতরে কনফিগারেশন প্যারামিটারগুলি ঘোষণামূলকভাবে সংজ্ঞায়িত করার জন্য আরও নিরাপদ ইন্টারফেসের পক্ষে। নতুন params মডিউলের সাহায্যে, CLI সমস্ত প্যারামিটারের একটি বৈধ মান না থাকলে স্থাপনা ব্লক করে, নিশ্চিত করে যে কোনও ফাংশন অনুপস্থিত কনফিগারেশন সহ স্থাপন করা হয়নি।

params সাবপ্যাকেজে মাইগ্রেট করুন

যদি আপনি functions.config দিয়ে পরিবেশ কনফিগারেশন ব্যবহার করে থাকেন, তাহলে আপনি আপনার বিদ্যমান কনফিগারেশনটিকে প্যারামিটারাইজড কনফিগারেশন হিসাবে রিফ্যাক্টর করে স্থানান্তর করতে পারেন। উদাহরণস্বরূপ:

আগে: ১ম প্রজন্ম

const functions = require("firebase-functions/v1");

exports.date = functions.https.onRequest((req, res) => {
  const date = new Date();
  const formattedDate =
date.toLocaleDateString(functions.config().dateformat);

  // ...
});

পরে: দ্বিতীয় প্রজন্ম

const {onRequest} = require("firebase-functions/v2/https");
const {defineString} = require("firebase-functions/params");

const dateFormat = defineString("DATE_FORMAT");

exports.date = onRequest((req, res) => {
  const date = new Date();
  const formattedDate = date.toLocaleDateString(dateFormat.value());

  // ...
});

প্যারামিটারের মান সেট করুন

প্রথমবার যখন আপনি স্থাপন করবেন, তখন Firebase CLI সমস্ত প্যারামিটারের মান জিজ্ঞাসা করবে এবং মানগুলি একটি dotenv ফাইলে সংরক্ষণ করবে। আপনার functions.config মানগুলি রপ্তানি করতে, firebase functions:config:export চালান।

অতিরিক্ত নিরাপত্তার জন্য, আপনি প্যারামিটারের ধরন এবং বৈধতা নিয়মও নির্দিষ্ট করতে পারেন।

বিশেষ ক্ষেত্রে: API কী

params মডিউলটি ক্লাউড সিক্রেট ম্যানেজারের সাথে একীভূত হয়, যা API কীগুলির মতো সংবেদনশীল মানগুলিতে সূক্ষ্ম অ্যাক্সেস নিয়ন্ত্রণ প্রদান করে। আরও তথ্যের জন্য গোপন প্যারামিটারগুলি দেখুন।

আগে: ১ম প্রজন্ম

const functions = require("firebase-functions/v1");

exports.getQuote = functions.https.onRequest(async (req, res) => {
  const quote = await fetchMotivationalQuote(functions.config().apiKey);
  // ...
});

পরে: দ্বিতীয় প্রজন্ম

const {onRequest} = require("firebase-functions/v2/https");
const {defineSecret} = require("firebase-functions/params");

// Define the secret parameter
const apiKey = defineSecret("API_KEY");

exports.getQuote = onRequest(
  // make the secret available to this function
  { secrets: [apiKey] },
  async (req, res) => {
    // retrieve the value of the secret
    const quote = await fetchMotivationalQuote(apiKey.value());
    // ...
  }
);

রানটাইম বিকল্প সেট করুন

রানটাইম অপশনের কনফিগারেশন ১ম এবং ২য় জেনারেশনের মধ্যে পরিবর্তিত হয়েছে। ২য় জেনারেশন সকল ফাংশনের জন্য অপশন সেট করার জন্য একটি নতুন ক্ষমতা যোগ করে।

আগে: ১ম প্রজন্ম

const functions = require("firebase-functions/v1");

exports.date = functions
  .runWith({
    // Keep 5 instances warm for this latency-critical function
    minInstances: 5,
  })
  // locate function closest to users
  .region("asia-northeast1")
  .https.onRequest((req, res) => {
    // ...
  });

exports.uppercase = functions
  // locate function closest to users and database
  .region("asia-northeast1")
  .firestore.document("my-collection/{docId}")
  .onCreate((change, context) => {
    // ...
  });

পরে: দ্বিতীয় প্রজন্ম

const {onRequest} = require("firebase-functions/v2/https");
const {onDocumentCreated} = require("firebase-functions/v2/firestore");
const {setGlobalOptions} = require("firebase-functions/v2");

// locate all functions closest to users
setGlobalOptions({ region: "asia-northeast1" });

exports.date = onRequest({
    // Keep 5 instances warm for this latency-critical function
    minInstances: 5,
  }, (req, res) => {
  // ...
});

exports.uppercase = onDocumentCreated("my-collection/{docId}", (event) => {
  /* ... */
});

ডিফল্ট পরিষেবা অ্যাকাউন্ট আপডেট করুন (ঐচ্ছিক)

ফায়ারবেস এপিআই-তে অ্যাক্সেস অনুমোদনের জন্য প্রথম প্রজন্মের ফাংশনগুলি গুগল অ্যাপ ইঞ্জিন ডিফল্ট পরিষেবা অ্যাকাউন্ট ব্যবহার করে, অন্যদিকে দ্বিতীয় প্রজন্মের ফাংশনগুলি কম্পিউট ইঞ্জিন ডিফল্ট পরিষেবা অ্যাকাউন্ট ব্যবহার করে। এই পার্থক্যের ফলে দ্বিতীয় প্রজন্মে স্থানান্তরিত ফাংশনগুলির জন্য অনুমতি সংক্রান্ত সমস্যা দেখা দিতে পারে, যদি আপনি প্রথম প্রজন্মের পরিষেবা অ্যাকাউন্টে বিশেষ অনুমতি প্রদান করেন। যদি আপনি কোনও পরিষেবা অ্যাকাউন্টের অনুমতি পরিবর্তন না করে থাকেন, তাহলে আপনি এই ধাপটি এড়িয়ে যেতে পারেন।

প্রস্তাবিত সমাধান হল, বিদ্যমান ১ম প্রজন্মের অ্যাপ ইঞ্জিন ডিফল্ট সার্ভিস অ্যাকাউন্টটি স্পষ্টভাবে সেই ফাংশনগুলিতে বরাদ্দ করা যা আপনি ২য় প্রজন্মের ডিফল্টকে অগ্রাহ্য করে ২য় প্রজন্মের ডিফল্টে মাইগ্রেট করতে চান। আপনি নিশ্চিত করতে পারেন যে প্রতিটি মাইগ্রেটেড ফাংশন serviceAccountEmail জন্য সঠিক মান সেট করে:

const {onRequest} = require("firebase-functions/https");
const {onDocumentCreated} = require("firebase-functions/v2/firestore");
const {setGlobalOptions} = require("firebase-functions");

// Use the App Engine default service account for all functions
setGlobalOptions({serviceAccountEmail: '<my-project-number>@<wbr>appspot.gserviceaccount.com'});

// Now I use the App Engine default service account.
exports.date = onRequest({cors: true}, (req, res) => {
  // ...
});

// I do too!
exports.uppercase = onDocumentCreated("my-collection/{docId}", (event) => {
  // ...
});

বিকল্পভাবে, আপনি অ্যাপ ইঞ্জিন ডিফল্ট পরিষেবা অ্যাকাউন্ট (প্রথম প্রজন্মের জন্য) এবং কম্পিউট ইঞ্জিন ডিফল্ট পরিষেবা অ্যাকাউন্ট (দ্বিতীয় প্রজন্মের জন্য) উভয়ের প্রয়োজনীয় সমস্ত অনুমতির সাথে মেলে পরিষেবা অ্যাকাউন্টের বিবরণ পরিবর্তন করতে পারেন।

কনকারেন্সি ব্যবহার করুন

দ্বিতীয় প্রজন্মের ফাংশনগুলির একটি উল্লেখযোগ্য সুবিধা হল একটি একক ফাংশন ইনস্ট্যান্সের একসাথে একাধিক অনুরোধ পরিবেশন করার ক্ষমতা। এটি শেষ ব্যবহারকারীদের দ্বারা অভিজ্ঞতার কোল্ড স্টার্টের সংখ্যা নাটকীয়ভাবে হ্রাস করতে পারে। ডিফল্টরূপে, কনকারেন্সি 80 এ সেট করা থাকে, তবে আপনি এটি 1 থেকে 1000 পর্যন্ত যেকোনো মান সেট করতে পারেন:

const {onRequest} = require("firebase-functions/v2/https");

exports.date = onRequest({
    // set concurrency value
    concurrency: 500
  },
  (req, res) => {
    // ...
});

কনকারেন্সি টিউন করলে কর্মক্ষমতা উন্নত হতে পারে এবং ফাংশনের খরচ কমতে পারে। কনকারেন্সি সম্পর্কে আরও জানুন "কনকারেন্সি অনুরোধগুলিকে অনুমতি দিন" বিভাগে।

বিশ্বব্যাপী চলক ব্যবহারের নিরীক্ষা করুন

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

আপগ্রেড করার সময়, আপনি আপনার ফাংশনের CPU কে gcf_gen1 এ সেট করতে পারেন এবং concurrency কে 1 এ সেট করতে পারেন যাতে প্রথম জেনারেশনের আচরণ পুনরুদ্ধার করা যায়:

const {onRequest} = require("firebase-functions/v2/https");

exports.date = onRequest({
    // TEMPORARY FIX: remove concurrency
    cpu: "gcf_gen1",
    concurrency: 1
  },
  (req, res) => {
    // ...
});

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

নতুন দ্বিতীয় প্রজন্মের ফাংশনগুলিতে ট্র্যাফিক স্থানান্তর করুন

ঠিক যেমন কোনও ফাংশনের অঞ্চল বা ট্রিগার টাইপ পরিবর্তন করার সময়, আপনাকে দ্বিতীয় প্রজন্মের ফাংশনটিকে একটি নতুন নাম দিতে হবে এবং ধীরে ধীরে ট্র্যাফিক এতে স্থানান্তর করতে হবে।

একই নামের ফাংশন ১ম থেকে ২য় জেনারেশনে আপগ্রেড করে firebase deploy চালানো সম্ভব নয়। এটি করলে ত্রুটি দেখা দেবে:

Upgrading from GCFv1 to GCFv2 is not yet supported. Please delete your old function or wait for this feature to be ready.

এই ধাপগুলি অনুসরণ করার আগে, প্রথমে নিশ্চিত করুন যে আপনার ফাংশনটি অকার্যকর , কারণ পরিবর্তনের সময় আপনার ফাংশনের নতুন সংস্করণ এবং পুরাতন সংস্করণ উভয়ই একই সময়ে চলবে। উদাহরণস্বরূপ, যদি আপনার ফায়ারস্টোরে একটি 1st gen ফাংশন থাকে যা ইভেন্ট লেখার জন্য প্রতিক্রিয়া জানায়, তাহলে নিশ্চিত করুন যে কোনও লেখার জন্য দুবার সাড়া দেওয়া হচ্ছে, একবার 1st gen ফাংশন দ্বারা এবং একবার 2nd gen ফাংশন দ্বারা, সেই ইভেন্টগুলির প্রতিক্রিয়া হিসাবে আপনার অ্যাপটি একটি সামঞ্জস্যপূর্ণ অবস্থায় রয়েছে।

  1. আপনার ফাংশন কোডে ফাংশনটির নাম পরিবর্তন করুন। উদাহরণস্বরূপ, resizeImage এর নাম পরিবর্তন করে resizeImageSecondGen
  2. ফাংশনটি এমনভাবে স্থাপন করুন যাতে মূল ১ম জেনারেশন ফাংশন এবং ২য় জেনারেশন ফাংশন উভয়ই চলমান থাকে।
    1. কলেবল, টাস্ক কিউ এবং HTTP ট্রিগারের ক্ষেত্রে, ক্লায়েন্ট কোডটি ২য় জেনার ফাংশনের নাম বা URL দিয়ে আপডেট করে সমস্ত ক্লায়েন্টকে ২য় জেনার ফাংশনের দিকে নির্দেশ করা শুরু করুন।
    2. ব্যাকগ্রাউন্ড ট্রিগারের সাহায্যে, প্রথম জেনারেশন এবং দ্বিতীয় জেনারেশন উভয় ফাংশনই স্থাপনের সাথে সাথে প্রতিটি ইভেন্টে সাড়া দেবে।
  3. সমস্ত ট্র্যাফিক মাইগ্রেট করা হয়ে গেলে, firebase CLI এর firebase functions:delete কমান্ড ব্যবহার করে প্রথম জেন ফাংশনটি মুছে ফেলুন।
    1. ঐচ্ছিকভাবে, ১ম জেনার ফাংশনের নামের সাথে মিল রেখে ২য় জেনার ফাংশনের নাম পরিবর্তন করুন।