1. قبل از شروع
یک برنامه افزودنی Firebase یک کار خاص یا مجموعه ای از وظایف را در پاسخ به درخواست های HTTP یا راه اندازی رویدادهایی از سایر محصولات Firebase و Google مانند Firebase Cloud Messaging، Cloud Firestore یا Pub/Sub انجام می دهد.
چیزی که خواهی ساخت
در این کد لبه، یک افزونه Firebase برای geohashing میسازید. پس از استقرار، برنامه افزودنی شما سپس مختصات X و Y را در پاسخ به رویدادهای Firestore یا از طریق فراخوانی تابع قابل فراخوانی به geohash تبدیل می کند. این می تواند به عنوان جایگزینی برای اجرای کتابخانه geofire در تمام پلتفرم های هدف شما برای ذخیره داده ها استفاده شود و در وقت شما صرفه جویی شود.
چیزی که یاد خواهید گرفت
- چگونه کدهای Cloud Functions موجود را بگیریم و آن را به یک افزونه Firebase قابل توزیع تبدیل کنیم
- چگونه یک فایل
extension.yaml
راه اندازی کنیم - نحوه ذخیره رشته های حساس (کلیدهای API) در یک برنامه افزودنی
- چگونه به توسعه دهندگان برنامه افزودنی اجازه دهیم آن را مطابق با نیازهای خود پیکربندی کنند
- نحوه آزمایش و استقرار افزونه
آنچه شما نیاز دارید
- Firebase CLI (نصب و ورود به سیستم)
- یک حساب Google، مانند یک حساب کاربری جیمیل
- Node.js و
npm
- محیط توسعه مورد علاقه شما
2. راه اندازی شوید
کد را دریافت کنید
هر چیزی که برای این افزونه نیاز دارید در یک مخزن GitHub است. برای شروع، کد را بردارید و آن را در محیط توسعه مورد علاقه خود باز کنید.
- فایل فشرده دانلود شده را باز کنید.
- برای نصب وابستگی های مورد نیاز، ترمینال را در پوشه
functions
باز کنید و دستورnpm install
را اجرا کنید.
Firebase را راه اندازی کنید
این کد لبه استفاده از شبیه سازهای Firebase را بسیار تشویق می کند. اگر میخواهید توسعه برنامههای افزودنی را با یک پروژه Firebase واقعی امتحان کنید، به ایجاد پروژه Firebase مراجعه کنید. این کد لبه از توابع ابری استفاده می کند، بنابراین اگر به جای شبیه سازها از یک پروژه Firebase واقعی استفاده می کنید، باید به برنامه قیمت گذاری Blaze ارتقا دهید .
آیا می خواهید به جلو بروید؟
شما می توانید نسخه تکمیل شده کد لبه را دانلود کنید. اگر در طول مسیر گیر کردید یا اگر میخواهید ببینید که یک برنامه افزودنی تکمیلشده چگونه به نظر میرسد، شاخه codelab-end
مخزن GitHub را بررسی کنید یا فایل فشرده تکمیلشده را دانلود کنید.
3. کد را مرور کنید
- فایل
index.ts
را از فایل فشرده باز کنید. توجه داشته باشید که شامل دو اعلان عملکرد ابری در آن است.
این توابع چه کار می کنند؟
این توابع نمایشی برای geohashing استفاده می شود. آنها یک جفت مختصات را می گیرند و آنها را به قالبی تبدیل می کنند که برای پرس و جوهای جغرافیایی در Firestore بهینه شده است. توابع استفاده از یک فراخوانی API را شبیهسازی میکنند تا بتوانید درباره مدیریت انواع دادههای حساس در برنامههای افزودنی اطلاعات بیشتری کسب کنید. برای اطلاعات بیشتر، به مستندات مربوط به اجرای جستارهای Geo بر روی داده ها در Firestore مراجعه کنید.
ثابت های تابع
ثابت ها در اوایل، در بالای فایل index.ts
اعلام می شوند. برخی از این ثابت ها در محرک های تعریف شده برنامه افزودنی ارجاع می شوند.
index.ts
import {firestore} from "firebase-functions";
import {initializeApp} from "firebase-admin/app";
import {GeoHashService, ResultStatusCode} from "./fake-geohash-service";
import {onCall} from "firebase-functions/v1/https";
import {fieldValueExists} from "./utils";
const documentPath = "users/{uid}";
const xField = "xv";
const yField = "yv";
const apiKey = "1234567890";
const outputField = "hash";
initializeApp();
const service = new GeoHashService(apiKey);
ماشه Firestore
اولین تابع در فایل index.ts
به شکل زیر است:
index.ts
export const locationUpdate = firestore.document(documentPath)
.onWrite((change) => {
// item deleted
if (change.after == null) {
return 0;
}
// double check that both values exist for computation
if (
!fieldValueExists(change.after.data(), xField) ||
!fieldValueExists(change.after.data(), yField)
) {
return 0;
}
const x: number = change.after.data()![xField];
const y: number = change.after.data()![yField];
const hash = service.convertToHash(x, y);
// This is to check whether the hash value has changed. If
// it hasn't, you don't want to write to the document again as it
// would create a recursive write loop.
if (fieldValueExists(change.after.data(), outputField)
&& change.after.data()![outputField] == hash) {
return 0;
}
return change.after.ref
.update(
{
[outputField]: hash.hash,
}
);
});
این تابع یک تریگر Firestore است. هنگامی که یک رویداد نوشتن در پایگاه داده رخ می دهد، تابع با جستجوی یک فیلد xv
و یک فیلد yv
به آن رویداد واکنش نشان می دهد، و اگر هر دوی این فیلدها وجود داشته باشند، geohash را محاسبه کرده و خروجی را در محل خروجی سند مشخص می نویسد. سند ورودی با ثابت users/{uid}
تعریف میشود، به این معنی که تابع هر سند نوشته شده برای users/
مجموعه را میخواند و سپس یک geohash برای آن اسناد پردازش میکند. سپس هش را به یک فیلد هش در همان سند خروجی می دهد.
توابع قابل فراخوانی
تابع بعدی در فایل index.ts
به شکل زیر است:
index.ts
export const callableHash = onCall((data, context) => {
if (context.auth == undefined) {
return {error: "Only authorized users are allowed to call this endpoint"};
}
const x = data[xField];
const y = data[yField];
if (x == undefined || y == undefined) {
return {error: "Either x or y parameter was not declared"};
}
const result = service.convertToHash(x, y);
if (result.status != ResultStatusCode.ok) {
return {error: `Something went wrong ${result.message}`};
}
return {result: result.hash};
});
به عملکرد onCall
توجه کنید. این نشان می دهد که این تابع یک تابع قابل فراخوانی است که می تواند از داخل کد برنامه مشتری شما فراخوانی شود. این تابع قابل فراخوانی پارامترهای x
و y
را می گیرد و یک geohash برمی گرداند. اگرچه این تابع مستقیماً در این Codelab فراخوانی نمی شود، اما به عنوان نمونه ای از چیزی برای پیکربندی در افزونه Firebase در اینجا گنجانده شده است.
4. یک فایل extension.yaml راه اندازی کنید
اکنون که می دانید کد توابع ابری در برنامه افزودنی شما چه می کند، آماده هستید تا آن را برای توزیع بسته بندی کنید. هر افزونه Firebase با یک فایل extension.yaml
ارائه می شود که توضیح می دهد برنامه افزودنی چه کاری انجام می دهد و چگونه رفتار می کند.
یک فایل extension.yaml
به برخی فراداده اولیه در مورد پسوند شما نیاز دارد. هر یک از مراحل زیر به شما کمک می کند تا بفهمید همه زمینه ها به چه معنا هستند و چرا به آنها نیاز دارید.
- یک فایل
extension.yaml
در فهرست اصلی پروژه ای که قبلا دانلود کرده اید ایجاد کنید. با اضافه کردن موارد زیر شروع کنید:
name: geohash-ext
version: 0.0.1
specVersion: v1beta # Firebase Extensions specification version (do not edit)
نام برنامه افزودنی به عنوان پایه شناسه نمونه برنامه افزودنی استفاده می شود (کاربران می توانند چندین نمونه از یک برنامه افزودنی را نصب کنند که هر کدام شناسه خاص خود را دارند). سپس Firebase نام حسابهای سرویس برنامه افزودنی و منابع ویژه برنامه افزودنی را با استفاده از آن شناسه نمونه تولید میکند. شماره نسخه نشان دهنده نسخه افزونه شما است. باید از نسخهسازی معنایی پیروی کند، و هر زمان که تغییراتی در عملکرد برنامه افزودنی ایجاد میکنید باید آن را بهروزرسانی کنید. نسخه مشخصات افزونه برای تعیین اینکه کدام مشخصات افزونه Firebase باید دنبال شود استفاده می شود، در این مورد از v1beta
استفاده می شود.
- برخی از جزئیات کاربر پسند را به فایل YAML اضافه کنید:
...
displayName: Latitude and longitude to GeoHash converter
description: A converter for changing your Latitude and longitude coordinates to geohashes.
هنگامی که توسعه دهندگان با برنامه افزودنی شما تعامل دارند، نام نمایشی نمایشی دوستانه از نام برنامه افزودنی شما است. توضیحات یک نمای کلی از آنچه افزونه انجام می دهد ارائه می دهد. هنگامی که برنامه افزودنی در extensions.dev مستقر می شود، چیزی شبیه به این به نظر می رسد:
- مجوز کد موجود در پسوند خود را مشخص کنید.
...
license: Apache-2.0 # The license you want for the extension
- مشخص کنید چه کسی افزونه را نوشته است و آیا برای نصب آن نیاز به صدور صورتحساب است یا خیر:
...
author:
authorName: AUTHOR_NAME
url: https://github.com/Firebase
billingRequired: true
از بخش author
استفاده میشود تا کاربران شما بدانند در صورتی که با برنامه افزودنی مشکل دارند یا اطلاعات بیشتری در مورد آن میخواهند با چه کسی تماس بگیرند. billingRequired
یک پارامتر ضروری است و باید روی true
تنظیم شود، زیرا همه برنامههای افزودنی به Cloud Functions متکی هستند که به طرح Blaze نیاز دارد.
این حداقل تعداد فیلدهای مورد نیاز در فایل extension.yaml
برای شناسایی این پسوند را پوشش می دهد. برای جزئیات بیشتر در مورد سایر اطلاعات شناسایی که می توانید در یک برنامه افزودنی مشخص کنید، به مستندات مراجعه کنید.
5. کد توابع ابری را به یک منبع Extensions تبدیل کنید
منبع افزونه آیتمی است که Firebase در طول نصب برنامه افزودنی در پروژه ایجاد می کند. سپس برنامه افزودنی مالک آن منابع است و یک حساب سرویس خاص دارد که روی آنها کار می کند. در این پروژه، آن منابع، توابع ابری هستند که باید در فایل extension.yaml
تعریف شوند، زیرا پسوند به طور خودکار منابع را از کد موجود در پوشه توابع ایجاد نمی کند. اگر توابع Cloud شما به صراحت به عنوان یک منبع اعلام نشده باشند، نمیتوان آنها را در هنگام استقرار برنامه افزودنی مستقر کرد.
مکان استقرار تعریف شده توسط کاربر
- به کاربر اجازه میدهد مکانی را که میخواهد این برنامه افزودنی را در آن مستقر کند، مشخص کند و تصمیم بگیرد که بهتر است برنامه افزودنی را نزدیکتر به کاربران نهایی خود میزبانی کند یا نزدیکتر به پایگاه داده خود. در فایل
extension.yaml
، گزینه انتخاب مکان را قرار دهید.
extension.yaml
اکنون آماده نوشتن پیکربندی برای منبع تابع هستید.
- در فایل
extension.yaml
، یک شی منبع برای تابعlocationUpdate
ایجاد کنید. موارد زیر را به فایلextension.yaml
اضافه کنید:
resources:
- name: locationUpdate
type: firebaseextensions.v1beta.function
properties:
eventTrigger:
eventType: providers/cloud.firestore/eventTypes/document.write
resource: projects/${PROJECT_ID}/databases/(default)/documents/users/{uid}
شما name
را به عنوان نام تابع تعریف شده در فایل index.ts
پروژه تعریف می کنید. شما type
تابعی را که در حال استقرار است، مشخص میکنید که همیشه باید firebaseextensions.v1beta.function
باشد. سپس، properties
این تابع را تعریف می کنید. اولین خاصیتی که تعریف می کنید eventTrigger
است که با این تابع مرتبط است. برای انعکاس آنچه برنامه افزودنی در حال حاضر پشتیبانی می کند، از eventType
of providers/cloud.firestore/eventTypes/document.write
استفاده می کنید که در Write Cloud Functions برای اسناد برنامه افزودنی شما یافت می شود. شما resource
را به عنوان محل اسناد تعریف می کنید. از آنجایی که هدف فعلی شما انعکاس آنچه در کد وجود دارد است، مسیر سند به users/{uid}
گوش میدهد و مکان پایگاه داده پیشفرض قبل از آن قرار دارد.
- افزونه نیاز به مجوز خواندن و نوشتن برای پایگاه داده Firestore دارد. در انتهای فایل
extension.yaml
، نقشهای IAM را مشخص کنید که برنامه افزودنی باید به آنها دسترسی داشته باشد تا بتواند با پایگاه داده در پروژه Firebase توسعهدهنده کار کند.
roles:
- role: datastore.user
reason: Allows the extension to read / write to your Firestore instance.
نقش datastore.user
از لیست نقش های پشتیبانی شده IAM برای برنامه های افزودنی می آید. از آنجایی که برنامه افزودنی خواندن و نوشتن است، نقش datastore.user
در اینجا مناسب است.
- تابع قابل فراخوانی نیز باید اضافه شود. در فایل
extension.yaml
، یک منبع جدید تحت ویژگی منابع ایجاد کنید. این ویژگی ها برای یک تابع قابل فراخوانی خاص هستند:
- name: callableHash
type: firebaseextensions.v1beta.function
properties:
httpsTrigger: {}
اگرچه منبع قبلی از یک eventTrigger
استفاده میکرد، در اینجا شما از یک httpsTrigger
استفاده میکنید که هم توابع قابل فراخوان و هم توابع HTTPS را پوشش میدهد.
بررسی کد
این پیکربندی بسیار زیادی بود تا extension.yaml
شما با همه چیزهایی که کد موجود در فایل index.ts
شما انجام میشود مطابقت دهد. فایل extension.yaml
تکمیل شده در این زمان باید به این صورت باشد:
extension.yaml
name: geohash-ext
version: 0.0.1
specVersion: v1beta # Firebase Extensions specification version (do not edit)
displayName: Latitude and Longitude to GeoHash converter
description: A converter for changing your Latitude and Longitude coordinates to geohashes.
license: Apache-2.0 # The license you want for the extension
author:
authorName: Sparky
url: https://github.com/Firebase
billingRequired: true
resources:
- name: locationUpdate
type: firebaseextensions.v1beta.function
properties:
eventTrigger:
eventType: providers/cloud.firestore/eventTypes/document.write
resource: projects/${PROJECT_ID}/databases/(default)/documents/users/{uid}
- name: callableHash
type: firebaseextensions.v1beta.function
properties:
httpsTrigger: {}
roles:
- role: datastore.user
reason: Allows the extension to read / write to your Firestore instance.
بررسی وضعیت
در این مرحله، بخشهای کاربردی اولیه برنامه افزودنی را تنظیم کردهاید، بنابراین میتوانید با استفاده از شبیهسازهای Firebase آن را امتحان کنید!
- اگر قبلاً این کار را نکردهاید،
npm run build
در پوشه توابع پروژه برنامههای افزودنی دانلود شده فراخوانی کنید. - یک دایرکتوری جدید در سیستم میزبان خود ایجاد کنید و آن دایرکتوری را با استفاده از
firebase init
به پروژه Firebase خود متصل کنید.
cd .. mkdir sample-proj cd sample-proj firebase init --project=projectID-or-alias
This command creates a `firebase.json` file in the directory. In the following steps, you push the configuration specified in this file to Firebase.
- از همان دایرکتوری،
firebase ext:install
اجرا کنید./path/to/extension
را با مسیر مطلق دایرکتوری که حاوی فایلextension.yaml
شما است جایگزین کنید.
firebase ext:install /path/to/extension
This command does two things:
- از شما می خواهد که پیکربندی را برای نمونه پسوند مشخص کنید، و یک فایل
*.env
ایجاد می کند که حاوی اطلاعات پیکربندی برای نمونه است. - این نمونه برنامه افزودنی را به بخش
extensions
firebase.json
شما اضافه می کند. این به عنوان نقشه شناسه نمونه به نسخه افزونه عمل می کند. - از آنجایی که پروژه را به صورت محلی اجرا می کنید، می توانید مشخص کنید که می خواهید از یک فایل محلی به جای Google Cloud Secret Manager استفاده کنید.
- شبیه سازهای Firebase را با پیکربندی جدید راه اندازی کنید:
firebase emulators:start
- پس از اجرای
emulators:start
، به تب Firestore در نمای وب شبیه سازها بروید. - سندی را با فیلد شماره
xv
و فیلد شمارهyv
به مجموعهusers
اضافه کنید.
- اگر در نصب افزونه موفق بودید، افزونه فیلد جدیدی به نام
hash
در سند ایجاد می کند.
برای جلوگیری از درگیری تمیز کنید
- پس از انجام آزمایش، برنامه افزودنی را حذف نصب کنید—شما قصد دارید کد برنامه افزودنی را به روز کنید و نمی خواهید بعداً با افزونه فعلی تداخل داشته باشید.
برنامههای افزودنی اجازه میدهند چندین نسخه از یک برنامه افزودنی به طور همزمان نصب شوند، بنابراین با حذف نصب، اطمینان حاصل میکنید که هیچ تداخلی با برنامه افزودنی نصبشده قبلی وجود ندارد.
firebase ext:uninstall geohash-ext
راه حل فعلی کار می کند، اما همانطور که در ابتدای پروژه ذکر شد، یک کلید API با کد سخت برای شبیه سازی ارتباط با یک سرویس وجود دارد. چگونه می توانید از کلید API کاربر نهایی به جای کلید ارائه شده اصلی استفاده کنید؟ ادامه مطلب را بخوانید تا متوجه شوید.
6. کاربر برنامه افزودنی را قابل تنظیم کنید
در این مرحله از Codelab، یک پسوند دارید که برای استفاده با تنظیمات نظری توابعی که قبلاً نوشتهاید، پیکربندی شده است، اما اگر کاربر شما بخواهد از طول و عرض جغرافیایی به جای y و x برای فیلدهایی که نشاندهنده موقعیت در هواپیمای دکارتی؟ همچنین، چگونه میتوانید کاربر نهایی را وادار کنید تا کلید API خود را عرضه کند، نه اینکه اجازه دهید کلید API ارائه شده را مصرف کند؟ شما می توانید به سرعت از سهمیه آن API فراتر بروید. در این مورد، شما پارامترها را تنظیم و استفاده می کنید.
پارامترهای اساسی را در فایل extension.yaml
تعریف کنید
با تبدیل مواردی که توسعه دهندگان ممکن است پیکربندی سفارشی برای آنها داشته باشند، شروع کنید. اولین پارامتر XFIELD
و YFIELD
خواهد بود.
- در فایل
extension.yaml
کد زیر را اضافه کنید که از پارامترهای فیلدXFIELD
وYFIELD
استفاده می کند. این پارامترها در داخل ویژگی YAMLparams
تعریف شده قبلی زندگی می کنند:
extension.yaml
params:
- param: XFIELD
label: The X Field Name
description: >-
The X Field is also known as the **longitude** value. What does
your Firestore instance refer to as the X value or the longitude
value. If no value is specified, the extension searches for
field 'xv'.
type: string
validationRegex: ^\D([0-9a-zA-Z_.]{0,375})$
validationErrorMessage: >-
The field can only contain uppercase or lowercase letter, numbers,
_, and . characters and must be less than 1500 bytes long. The field
must also not start with a number.
default: xv
required: false
immutable: false
example: xv
- param: YFIELD
label: The Y Field Name
description: >-
The Y Field is also known as the **latitude** value. What does
your Firestore instance refer to as the Y value or the latitude
value. If no value is specified, the extension searches for
field 'yv'.
type: string
validationRegex: ^\D([0-9a-zA-Z_.]{0,375})$
validationErrorMessage: >-
The field can only contain uppercase or lowercase letter, numbers,
_, and . characters and must be less than 1500 bytes long. The field
must also not start with a number.
default: yv
required: false
immutable: false
example: yv
- param پارامتر را به گونه ای نامگذاری می کند که برای شما، تولید کننده برنامه افزودنی قابل مشاهده باشد. بعداً هنگام تعیین مقادیر پارامتر از این مقدار استفاده کنید.
- label یک شناسه قابل خواندن توسط انسان برای توسعه دهنده است تا به آنها اطلاع دهد که این پارامتر چه کاری انجام می دهد.
- توضیحات توضیحات مفصلی از مقدار می دهد. از آنجایی که این از نشانه گذاری پشتیبانی می کند، می تواند به اسناد اضافی پیوند داده شود، یا می تواند کلماتی را که ممکن است برای توسعه دهنده مهم باشند برجسته کند.
- type مکانیسم ورودی را برای نحوه تنظیم مقدار پارامتر توسط کاربر تعریف می کند. انواع زیادی وجود دارد، از جمله
string
،select
،multiSelect
،selectResource
وsecret
. برای کسب اطلاعات بیشتر در مورد هر یک از این گزینه ها، به مستندات مراجعه کنید. - validationRegex ورودی توسعهدهنده را به یک مقدار regex خاص محدود میکند (در مثال بر اساس دستورالعملهای ساده نام فیلد موجود در اینجا است). و اگر شکست ...
- validationErrorMessage به توسعه دهنده از مقدار خرابی هشدار می دهد.
- پیشفرض مقداری است که اگر توسعهدهنده متنی را وارد نکند، مقدار آن چقدر خواهد بود.
- الزامی به این معنی است که توسعه دهنده نیازی به وارد کردن متن ندارد.
- imutable به توسعه دهنده اجازه می دهد تا این افزونه را به روز کند و این مقدار را تغییر دهد. در این مورد، توسعه دهنده باید بتواند نام فیلدها را با تغییر نیازمندی های آنها تغییر دهد.
- مثال ایده ای از اینکه یک ورودی معتبر ممکن است شبیه باشد را ارائه می دهد.
این خیلی قابل درک بود!
- قبل از افزودن یک پارامتر خاص، باید سه پارامتر دیگر را به فایل
extension.yaml
اضافه کنید.
- param: INPUTPATH
label: The input document to listen to for changes
description: >-
This is the document where you write an x and y value to. Once
that document has received a value, it notifies the extension to
calculate a geohash and store that in an output document in a certain
field. This accepts function [wildcard parameters](https://firebase.google.com/docs/functions/firestore-events#wildcards-parameters)
type: string
validationRegex: ^[^/]+(/[^/]*/[^/]*)*/[^/]+$
validationErrorMessage: >-
This must point to a document path, not a collection path from the root
of the database. It must also not start or end with a '/' character.
required: true
immutable: false
example: users/{uid}
- param: OUTPUTFIELD
label: Geohash field
description: >-
This specifies the field in the output document to store the geohash in.
type: string
validationRegex: ^\D([0-9a-zA-Z_.]{0,375})$
validationErrorMessage: >-
The field can only contain uppercase or lowercase letter, numbers,
_, and . characters and must be less than 1500 bytes long. The field
must also not start with a number.
required: false
default: hash
immutable: false
example: hash
تعریف پارامترهای حساس
اکنون باید کلید API را که کاربر مشخص می کند مدیریت کنید. این یک رشته حساس است که نباید به صورت متن ساده در تابع ذخیره شود. در عوض، این مقدار را در مدیر مخفی Cloud ذخیره کنید. این مکان ویژه ای در ابر است که اسرار رمزگذاری شده را ذخیره می کند و از افشای تصادفی آنها جلوگیری می کند. این امر مستلزم پرداخت هزینه برای استفاده از این سرویس از سوی توسعهدهنده است، اما یک لایه امنیتی اضافی بر روی کلیدهای API آنها اضافه میکند و به طور بالقوه فعالیتهای جعلی را محدود میکند. مستندات کاربر به توسعه دهنده هشدار می دهد که این یک سرویس پولی است، به طوری که هیچ گونه شگفتی در صورتحساب وجود ندارد. به طور کلی، استفاده مشابه سایر منابع رشته ای است که در بالا ذکر شد. تنها تفاوت در نوعی است که به آن secret
می گویند.
- در فایل
extension.yaml
کد زیر را اضافه کنید:
extension.yaml
- param: APIKEY
label: GeohashService API Key
description: >-
Your geohash service API Key. Since this is a demo, and not a real
service, you can use : 1234567890.
type: secret
required: true
immutable: false
برای استفاده از پارامترها، ویژگی های resource
را به روز کنید
همانطور که قبلا ذکر شد، منبع (نه تابع) نحوه مشاهده منبع را مشخص می کند، بنابراین منبع locationUpdate
برای استفاده از پارامتر جدید باید به روز شود.
- در فایل
extension.yaml
کد زیر را اضافه کنید:
extension.yaml
## Change from this
- name: locationUpdate
type: firebaseextensions.v1beta.function
properties:
eventTrigger:
eventType: providers/cloud.firestore/eventTypes/document.write
resource: projects/${PROJECT_ID}/databases/(default)/documents/users/{uid}]
## To this
- name: locationUpdate
type: firebaseextensions.v1beta.function
properties:
eventTrigger:
eventType: providers/cloud.firestore/eventTypes/document.write
resource: projects/${PROJECT_ID}/databases/(default)/documents/${INPUTPATH}
فایل extension.yaml
را بررسی کنید
- فایل
extension.yaml
را مرور کنید. باید چیزی شبیه این باشد:
extension.yaml
name: geohash-ext
version: 0.0.1
specVersion: v1beta # Firebase Extensions specification version (do not edit)
displayName: Latitude and Longitude to GeoHash converter
description: A converter for changing your Latitude and Longitude coordinates to geohashes.
license: Apache-2.0 # The license you want to use for the extension
author:
authorName: Sparky
url: https://github.com/Firebase
billingRequired: true
params:
- param: XFIELD
label: The X Field Name
description: >-
The X Field is also known as the **longitude** value. What does
your Firestore instance refer to as the X value or the longitude
value. If you don't provide a value for this field, the extension will use 'xv' as the default value.
type: string
validationRegex: ^\D([0-9a-zA-Z_.]{0,375})$
validationErrorMessage: >-
The field can only contain uppercase or lowercase letter, numbers,
_, and . characters and must be less than 1500 bytes long. The field
must also not start with a number.
default: xv
required: false
immutable: false
example: xv
- param: YFIELD
label: The Y Field Name
description: >-
The Y Field is also known as the **latitude** value. What does
your Firestore instance refer to as the Y value or the latitude
Value. If you don't provide a value for this field, the extension will use 'yv' as the default value.
type: string
validationRegex: ^\D([0-9a-zA-Z_.]{0,375})$
validationErrorMessage: >-
The field can only contain uppercase or lowercase letter, numbers,
_, and . characters and must be less than 1500 bytes long. The field
must also not start with a number.
default: yv
required: false
immutable: false
example: yv
- param: INPUTPATH
label: The input document to listen to for changes
description: >-
This is the document where you write an x and y value to. Once
that document has been modified, it notifies the extension to
compute a geohash and store that in an output document in a certain
field. This accepts function [wildcard parameters](https://firebase.google.com/docs/functions/firestore-events#wildcards-parameters)
type: string
validationRegex: ^[^/]+(/[^/]*/[^/]*)*/[^/]+$
validationErrorMessage: >-
This must point to a document path, not a collection path from the root
of the database. It must also not start or end with a '/' character.
required: true
immutable: false
example: users/{uid}
- param: OUTPUTFIELD
label: Geohash field
description: >-
This specifies the field in the output document to store the geohash in.
type: string
validationRegex: ^\D([0-9a-zA-Z_.]{0,375})$
validationErrorMessage: >-
The field can only contain uppercase or lowercase letter, numbers,
_, and . characters and must be less than 1500 bytes long. The field
must also not start with a number.
required: false
default: hash
immutable: false
example: hash
- param: APIKEY
label: GeohashService API Key
description: >-
Your geohash service API Key. Since this is a demo, and not a real
service, you can use : 1234567890.
type: secret
required: true
immutable: false
resources:
- name: locationUpdate
type: firebaseextensions.v1beta.function
properties:
eventTrigger:
eventType: providers/cloud.firestore/eventTypes/document.write
resource: projects/${PROJECT_ID}/databases/(default)/documents/${INPUTPATH}
- name: callableHash
type: firebaseextensions.v1beta.function
properties:
httpsTrigger: {}
roles:
- role: datastore.user
reason: Allows the extension to read / write to your Firestore instance.
دسترسی به پارامترها در کد
اکنون که تمام پارامترها در فایل extension.yaml
پیکربندی شده اند، آنها را به فایل index.ts
اضافه کنید.
- در فایل
index.ts
، مقادیر پیشفرض را باprocess.env.PARAMETER_NAME
جایگزین کنید، که مقادیر پارامتر مناسب را واکشی میکند و آنها را در کد تابع مستقر در پروژه Firebase توسعهدهنده پر میکند.
index.ts
// Replace this:
const documentPath = "users/{uid}";
const xField = "xv";
const yField = "yv";
const apiKey = "1234567890";
const outputField = "hash";
// with this:
const documentPath = process.env.INPUTPATH!; // this value is ignored since its read from the resource
const xField = process.env.XFIELD!;
const yField = process.env.YFIELD!;
const apiKey = process.env.APIKEY!;
const outputField = process.env.OUTPUTFIELD!;
به طور معمول، شما می خواهید بررسی های تهی را با مقادیر متغیر محیطی انجام دهید، اما در این مورد، اطمینان دارید که مقادیر پارامترها به درستی کپی شده اند. کد اکنون برای کار با پارامترهای برنامه افزودنی پیکربندی شده است.
7. اسناد کاربر ایجاد کنید
قبل از آزمایش کد روی شبیهسازها یا در بازار افزونههای Firebase، برنامه افزودنی باید مستند باشد تا توسعهدهندگان بدانند هنگام استفاده از برنامه افزودنی چه چیزی دریافت میکنند.
- با ایجاد فایل
PREINSTALL.md
، که برای توصیف عملکرد، پیش نیازهای نصب و پیامدهای صورتحساب احتمالی استفاده می شود، شروع کنید.
PREINSTALL.md
Use this extension to automatically convert documents with a latitude and
longitude to a geohash in your database. Additionally, this extension includes a callable function that allows users to make one-time calls
to convert an x,y coordinate into a geohash.
Geohashing is supported for latitudes between 90 and -90 and longitudes
between 180 and -180.
#### Third Party API Key
This extension uses a fictitious third-party API for calculating the
geohash. You need to supply your own API keys. (Since it's fictitious,
you can use 1234567890 as an API key).
#### Additional setup
Before installing this extension, make sure that you've [set up a Cloud
Firestore database](https://firebase.google.com/docs/firestore/quickstart) in your Firebase project.
After installing this extension, you'll need to:
- Update your client code to point to the callable geohash function if you
want to perform arbitrary geohashes.
Detailed information for these post-installation tasks are provided after
you install this extension.
#### Billing
To install an extension, your project must be on the [Blaze (pay as you
go) plan](https://firebase.google.com/pricing)
- This extension uses other Firebase and Google Cloud Platform services,
which have associated charges if you exceed the service's no-cost tier:
- Cloud Firestore
- Cloud Functions (Node.js 16+ runtime. [See
FAQs](https://firebase.google.com/support/faq#extensions-pricing))
- [Cloud Secret Manager](https://cloud.google.com/secret-manager/pricing)
- برای صرفه جویی در زمان در نوشتن
README.md
برای این پروژه، از روش راحتی استفاده کنید:
firebase ext:info . --markdown > README.md
این ترکیبی از محتویات فایل PREINSTALL.md
شما و جزئیات بیشتر در مورد پسوند شما از فایل extension.yaml
شما است.
در نهایت، توسعه دهنده برنامه افزودنی را در مورد برخی از جزئیات اضافی در مورد برنامه افزودنی که به تازگی نصب شده است مطلع کنید. ممکن است توسعهدهنده دستورالعملها و اطلاعات بیشتری را پس از تکمیل نصب دریافت کند و ممکن است برخی از وظایف دقیق پس از نصب مانند تنظیم کد مشتری را در اینجا دریافت کند.
- یک فایل
POSTINSTALL.md
ایجاد کنید و سپس اطلاعات نصب پست زیر را وارد کنید:
POSTINSTALL.md
Congratulations on installing the geohash extension!
#### Function information
* **Firestore Trigger** - ${function:locationUpdate.name} was installed
and is invoked when both an x field (${param:XFIELD}) and y field
(${param:YFIELD}) contain a value.
* **Callable Trigger** - ${function:callableHash.name} was installed and
can be invoked by writing the following client code:
```javascript
import { getFunctions, httpsCallable } from "firebase/functions";
const functions = getFunctions();
const geoHash = httpsCallable(functions, '${function:callableHash.name}');
geoHash({ ${param:XFIELD}: -122.0840, ${param:YFIELD}: 37.4221 })
.then((result) => {
// Read result of the Cloud Function.
/** @type {any} */
const data = result.data;
const error = data.error;
if (error != null) {
console.error(`callable error : ${error}`);
}
const result = data.result;
console.log(result);
});
نظارت
به عنوان بهترین روش، میتوانید فعالیت برنامه افزودنی نصب شده خود، از جمله بررسی سلامت، استفاده و گزارشهای آن را نظارت کنید .
The output rendering looks something like this when it's deployed:
<img src="img/82b54a5c6ca34b3c.png" alt="A preview of the latitude and longitude geohash converter extension in the firebase console" width="957.00" />
## Test the extension with the full configuration
Duration: 03:00
It's time to make sure that the user-configurable extension is working the way it is intended.
* Change into the functions folder and ensure that the latest compiled version of the extensions exists. In the extensions project functions directory, call:
```console
npm run build
این توابع را مجدداً کامپایل می کند تا آخرین کد منبع برای استقرار در کنار برنامه افزودنی هنگامی که مستقیماً در یک شبیه ساز یا Firebase مستقر می شود آماده است.
بعد، یک دایرکتوری جدید برای آزمایش پسوند ایجاد کنید. از آنجایی که برنامه افزودنی از توابع موجود ایجاد شده است، از پوشه ای که افزونه در آن پیکربندی شده است آزمایش نکنید، زیرا تلاش می کند توابع و قوانین Firebase را در کنار آن مستقر کند.
با شبیه سازهای Firebase نصب و تست کنید
- یک دایرکتوری جدید در سیستم میزبان خود ایجاد کنید و آن دایرکتوری را با استفاده از
firebase init
به پروژه Firebase خود متصل کنید.
mkdir sample-proj cd sample-proj firebase init --project=projectID-or-alias
- از آن دایرکتوری،
firebase ext:install
را برای نصب افزونه اجرا کنید./path/to/extension
را با مسیر مطلق دایرکتوری که حاوی فایلextension.yaml
شما است جایگزین کنید. این فرآیند نصب برنامه افزودنی شما را شروع میکند و یک فایل.env
که حاوی تنظیمات شما است، قبل از فشار دادن پیکربندی به Firebase یا شبیهسازها ایجاد میکند.
firebase ext:install /path/to/extension
- از آنجایی که پروژه را به صورت محلی اجرا می کنید، مشخص کنید که می خواهید از یک فایل محلی به جای Google Cloud Secret Manager استفاده کنید.
- مجموعه شبیه ساز محلی را راه اندازی کنید:
firebase emulators:start
با یک پروژه Firebase واقعی نصب و آزمایش کنید
میتوانید برنامه افزودنی خود را در یک پروژه Firebase واقعی نصب کنید. توصیه می شود از یک پروژه آزمایشی برای تست خود استفاده کنید. اگر میخواهید جریان سرتاسر برنامه افزودنی خود را آزمایش کنید یا اگر راهانداز برنامه افزودنی شما هنوز توسط مجموعه شبیهساز Firebase پشتیبانی نمیشود، از این گردش کار آزمایشی استفاده کنید ( گزینه شبیهساز برنامههای افزودنی را ببینید). شبیهسازها در حال حاضر از توابع راهاندازی شده با درخواست HTTP و توابع راهاندازی رویدادهای پسزمینه برای Cloud Firestore، پایگاه داده بیدرنگ، و Pub/Sub پشتیبانی میکنند.
- یک دایرکتوری جدید در سیستم میزبان خود ایجاد کنید و آن دایرکتوری را با استفاده از
firebase init
به پروژه Firebase خود متصل کنید.
cd .. mkdir sample-proj cd sample-proj firebase init --project=projectID-or-alias
- سپس، از آن دایرکتوری،
firebase ext:install
برای نصب افزونه اجرا کنید./path/to/extension
را با مسیر مطلق دایرکتوری که حاوی فایلextension.yaml
شما است جایگزین کنید. این فرآیند نصب برنامه افزودنی شما را شروع میکند و یک فایل.env
که حاوی تنظیمات شما است، قبل از فشار دادن پیکربندی به Firebase یا شبیهسازها ایجاد میکند.
firebase ext:install /path/to/extension
- از آنجایی که می خواهید مستقیماً در Firebase مستقر شوید و می خواهید از Google Cloud Secret Manager استفاده کنید، باید قبل از نصب برنامه افزودنی Secret Manager API را فعال کنید .
- در پروژه Firebase خود مستقر شوید.
firebase deploy
افزونه را تست کنید
- پس از اجرای
firebase deploy
یاfirebase emulators:start
، به برگه Firestore کنسول Firebase یا نمای وب شبیه سازها بروید. - یک سند به مجموعه مشخص شده توسط فیلد
x
و فیلدy
اضافه کنید. در این مورد، اسناد به روز شده درu/{uid}
با یک فیلدx
xv
و یک فیلدy
ازyv
قرار دارند.
- اگر در نصب برنامه افزودنی موفق بودید، پس از ذخیره دو فیلد، پسوند فیلد جدیدی به نام
hash
در سند ایجاد می کند.
8. تبریک!
شما با موفقیت اولین تابع Cloud خود را به یک افزونه Firebase تبدیل کردید!
شما یک فایل extension.yaml
اضافه کردید و آن را پیکربندی کردید تا توسعه دهندگان بتوانند نحوه استقرار برنامه افزودنی شما را انتخاب کنند. سپس اسناد کاربر را ایجاد کردید که راهنمایی میکند که توسعهدهندگان برنامه افزودنی باید قبل از راهاندازی برنامه افزودنی چه اقداماتی را انجام دهند و پس از نصب موفقیتآمیز برنامه افزودنی، چه اقداماتی ممکن است انجام دهند.
اکنون مراحل کلیدی مورد نیاز برای تبدیل یک تابع Firebase به یک افزونه Firebase قابل توزیع را می دانید.