במאמר הזה מוסבר איך משביתים אוטומטית את החיוב בפרויקט כשהעלויות מגיעות לתקציב של הפרויקט או חורגות ממנו. כשמשביתים את החיוב בפרויקט, כל שירותי Google Cloud בפרויקט נפסקים, כולל שירותים שניתנים בתוכנית בחינם. במאמר שליטה בשימוש במשאבים באמצעות התראות מוסבר איך להגיב פרטנית להתראות בקשר לתקציב.
אם התקציב שלכם ל- Google Cloudמוגבל, אנחנו ממליצים להגביל את העלויות. בנוסף, אם תגיעו לרף העליון של התקציב, כדאי להשבית את כל שירותי Google Cloud כדי להפסיק להשתמש בהם ולא לצבור עוד עלויות בפרויקט.
מגבלות
יש עיכוב מסוים בין מועד צבירת העלויות בפועל ועד לרגע קבלת ההתראות בקשר לתקציב, כך שיכול להיות שתצברו עלויות נוספות על השימוש, שעדיין לא חויבו כשהפסקתם את כל השירותים. לכן, גם אם תבצעו את הפעולות שבדוגמה הזאת, עדיין יכול להיות שתחרגו מהתקציב. אם התקציב שלכם מוגבל, כדאי להגדיר את הרף העליון בסכום נמוך מהתקציב כדי להביא בחשבון עיכובים בחיוב.
אי אפשר להשבית את החיוב בפרויקט נעול בחשבון לחיוב. למידע נוסף על נעילה ופתיחה של פרויקטים, קראו את המאמר אבטחת הקישור בין פרויקט לחשבון שלו לחיוב.
סקריפט לדוגמה
אפשר להשתמש בסקריפט הבא כדי לבצע את כל השלבים במדריך הזה בסקריפט אחד. פשוט מעתיקים את הסקריפט הזה לקובץ Bash, עורכים את פרמטרי המשתמש בחלק העליון של הקובץ ומריצים את הסקריפט.
לוחצים כדי להרחיב את הסקריפט.
#!/bin/bash
# This script combines all the steps from the following documentation so they
# can be executed in a single command:
# https://docs.cloud.google.com/billing/docs/how-to/disable-billing-with-notifications#functions_cap_billing_dependencies-nodejs
# Step-by-step instructions:
# A) Edit the parameters under step 1 (Set User Parameters) below and then
# copy the contents of this file to your clipboard.
# B) Open Cloud Shell (or any bash terminal with gcloud installed) via the
# terminal icon in the top right of http://console.cloud.google.com
# C) Paste the contents into a new Bash file which you can do with the
# following commands:
# type "vi ./billing_caps.sh" to create a new file and open it for editing
# press 'i' to enter insert mode
# paste the contents of this file into the terminal (right-click + "paste")
# press 'ESC' to exit insert mode
# type ":wq" to save and exit
# type "chmod +x billing_caps.sh" to make the script executable
# C) Execute the script with the command "./billing_caps.sh"
# D) Monitor the terminal output for any errors that might require you to
# repeat one or more of the above steps. If no errors occur then you're done!
# 1. Set User Parameters
PROJECT_ID="your-project-id"
REGION="us-central1"
TOPIC_ID="billing-alerts-topic"
BILLING_ACCOUNT_ID="your-billing-account-id"
BUDGET_AMOUNT="100" # Example: $100
# 2. Enable Required APIs
gcloud services enable billingbudgets.googleapis.com \
cloudbilling.googleapis.com \
cloudbuild.googleapis.com \
cloudfunctions.googleapis.com \
eventarc.googleapis.com \
run.googleapis.com \
pubsub.googleapis.com \
artifactregistry.googleapis.com \
--project="${PROJECT_ID}"
# 3. Create Pub/Sub Topic
gcloud pubsub topics create "${TOPIC_ID}" --project="${PROJECT_ID}"
# 4. Create Source Files for the Function
mkdir -p billing_function
cat <<'EOF' > billing_function/package.json
{
"name": "cloud-functions-billing",
"private": "true",
"version": "0.0.1",
"description": "Examples of integrating Cloud Functions with billing",
"main": "index.js",
"engines": {
"node": ">=18.0.0"
},
"author": "Ace Nassri ",
"license": "Apache-2.0",
"dependencies": {
"@google-cloud/billing": "^4.0.0"
},
"devDependencies": {
"@google-cloud/functions-framework": "^3.0.0",
"c8": "^10.0.0",
"gaxios": "^6.0.0",
"mocha": "^10.0.0",
"promise-retry": "^2.0.0",
"proxyquire": "^2.1.0",
"sinon": "^18.0.0",
"wait-port": "^1.0.4"
}
}
EOF
cat <<'EOF' > billing_function/index.js
const {CloudBillingClient} = require('@google-cloud/billing');
const PROJECT_ID = process.env.GOOGLE_CLOUD_PROJECT;
const PROJECT_NAME = `projects/${PROJECT_ID}`;
const billing = new CloudBillingClient();
exports.stopBilling = async pubsubEvent => {
const pubsubData = JSON.parse(
Buffer.from(pubsubEvent.data, 'base64').toString()
);
if (pubsubData.costAmount <= pubsubData.budgetAmount) {
return `No action necessary. (Current cost: ${pubsubData.costAmount})`;
}
if (!PROJECT_ID) {
return 'No project specified';
}
const billingEnabled = await _isBillingEnabled(PROJECT_NAME);
if (billingEnabled) {
return _disableBillingForProject(PROJECT_NAME);
} else {
return 'Billing already disabled';
}
};
/**
* Determine whether billing is enabled for a project
* @param {string} projectName Name of project to check if billing is enabled
* @return {bool} Whether project has billing enabled or not
*/
const _isBillingEnabled = async projectName => {
try {
const [res] = await billing.getProjectBillingInfo({name: projectName});
return res.billingEnabled;
} catch (e) {
console.log(
'Unable to determine if billing is enabled on specified project, assuming billing is enabled'
);
return true;
}
};
/**
* Disable billing for a project by removing its billing account
* @param {string} projectName Name of project disable billing on
* @return {string} Text containing response from disabling billing
*/
const _disableBillingForProject = async projectName => {
const [res] = await billing.updateProjectBillingInfo({
name: projectName,
resource: {billingAccountName: ''}, // Disable billing
});
return `Billing disabled: ${JSON.stringify(res)}`;
};
EOF
# 5. Deploy the Cloud Run Function
# This uses the Gen 2 runtime as suggested by current standards
gcloud functions deploy stop-billing-function \
--gen2 \
--runtime=nodejs24 \
--region="${REGION}" \
--trigger-topic="${TOPIC_ID}" \
--entry-point=stopBilling \
--set-env-vars GOOGLE_CLOUD_PROJECT="${PROJECT_ID}" \
--source=./billing_function \
--project="${PROJECT_ID}"
# 6. Configure Service Account Permissions
# Get the service account associated with the function
SERVICE_ACCOUNT=$(gcloud functions describe stop-billing-function --region="${REGION}" --format="value(serviceConfig.serviceAccountEmail)" --project="${PROJECT_ID}")
# Grant the service account the "Billing Account Administrator" role on the
# billing account.
# Note: You must have 'Billing Account Administrator' rights to run this
gcloud billing accounts add-iam-policy-binding "${BILLING_ACCOUNT_ID}" \
--member="serviceAccount:${SERVICE_ACCOUNT}" \
--role="roles/billing.admin"
# 7. Create the Budget and Link to Topic
gcloud billing budgets create \
--billing-account="${BILLING_ACCOUNT_ID}" \
--display-name="Budget for ${PROJECT_ID}" \
--budget-amount="${BUDGET_AMOUNT}" \
--threshold-rule=percent=100 \
--notifications-rule-pubsub-topic="projects/${PROJECT_ID}/topics/${TOPIC_ID}"
echo "Setup complete. Billing will be disabled if costs exceed ${BUDGET_AMOUNT}."
לפני שמתחילים
לפני שאתם מתחילים תצטרכו לבצע את המשימות האלה:
- הפעלת Cloud Billing API
- יצירת תקציב שמוגבל לפרויקט אחד
- יצירת התראות פרוגרמטיות בקשר לתקציב
הגדרת פונקציית Cloud Run
כדי להשבית בפרויקט את כלי החיוב ב-Cloud, אתם צריכים ליצור פונקציית Cloud Run ולהגדיר אותה לקריאה ל-Cloud Billing API.
- פועלים לפי ההוראות שבמאמר יצירה של פונקציית Cloud Run. חשוב לוודא ש-Trigger type מוגדר כך שישתמש באותו נושא Pub/Sub שהוגדר לשימוש בתקציב.
מוסיפים את יחסי התלות הבאים:
Node.js
מעתיקים את הקוד הבא לקובץ
package.json:Python
מעתיקים את הקוד הבא לקובץ
requirements.txt:מעתיקים את הקוד הבא לפונקציית Cloud Run:
Node.js
Python
מגדירים את Entry point לפונקציה הנכונה להרצה:
Node.js
מגדירים את Entry point ל-
stopBilling.Python
מגדירים את Entry point ל-
stop_billing.בודקים את רשימת משתני הסביבה שמוגדרים אוטומטית כדי להחליט אם צריך להגדיר ידנית את המשתנה GOOGLE_CLOUD_PROJECT כך שיכיל את הפרויקט שבו רוצים להשבית את החיוב ב-Cloud.
לוחצים על DEPLOY.
הגדרת ההרשאות לחשבון השירות
פונקציית Cloud Run פועלת בתור חשבון שירות שנוצר אוטומטית. כדי להשבית את החיוב, צריך לתת לחשבון השירות הרשאות לכל השירותים בפרויקט שהוא אמור לשנות. כדי לעשות את זה, מבצעים את הפעולות האלה:
- מזהים את חשבון השירות הנכון. כדי לעשות את זה, אפשר לעיין בפרטים של פונקציית Cloud Run. חשבון השירות מופיע בתחתית הדף.
נכנסים לדף IAM במסוף Google Cloud כדי להגדיר את ההרשאות המתאימות.
כדי לשנות את ההרשאות בחשבון לחיוב, נכנסים לדף Account management בחלק של החיוב במסוף Google Cloud . אחר כך מוסיפים את חשבון השירות בתור חשבון ראשי בחשבון לחיוב ב-Cloud ומגדירים את ההרשאות המתאימות.
למידע נוסף על הגדרת הרשאות לחשבונות לחיוב ב-Cloud
בדיקה אם החיוב ב-Cloud מושבת
ברגע שתישלח התראה בקשר לתקציב, הפונקציה תתחיל לרוץ ואז יוסר הקישור בין הפרויקט שצוין לחשבון לחיוב ב-Cloud. כדי לוודא שהפונקציה פועלת כמו שצריך, מריצים בדיקה של פונקציית Cloud Run.
אם היא פועלת כמו שצריך, הפרויקט לא יופיע יותר בחשבון לחיוב ב-Cloud והמשאבים שכלולים בפרויקט יושבתו, כולל פונקציית Cloud Run שמשויכת לאותו הפרויקט.
כדי להמשיך להשתמש במשאבי Google Cloud בפרויקט, צריך להפעיל מחדש באופן ידני את החיוב ב-Cloud בשביל הפרויקט במסוףGoogle Cloud .
המאמרים הבאים
דוגמאות נוספות להתראות פרוגרמטיות, שיעזרו לכם ללמוד איך מבצעים את הפעולות הבאות: