Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Feat/gh action #63

Merged
merged 22 commits into from
Oct 11, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
82 changes: 82 additions & 0 deletions .github/workflows/ci-pr.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,82 @@
name: CI for Pull Requests

on:
pull_request:
branches:
- main # Run the workflow for PRs targeting the "main" branch

jobs:
test:
runs-on: ubuntu-latest

steps:
# Step 1: Check out the code from the PR branch
- name: Checkout code
uses: actions/checkout@v2

# Step 2: Set up Node.js
- name: Set up Node.js
uses: actions/setup-node@v3
with:
node-version: '20.x'

# Step 3: Install MBT and dependencies
- name: Install MBT and dependencies
run: |
npm install -g mbt
cd code
npm install --production

# Step 4: Install CF Cli
- name: Install CF Cli
run: |
wget -q -O - https://packages.cloudfoundry.org/debian/cli.cloudfoundry.org.key | gpg --dearmor -o /usr/share/keyrings/cli.cloudfoundry.org.gpg
echo "deb [trusted=yes] https://packages.cloudfoundry.org/debian stable main" | sudo tee /etc/apt/sources.list.d/cloudfoundry-cli.list
sudo apt-get update
sudo apt-get install cf8-cli

# Step 5: Download and Install SAP BTP CLI
- name: Install BTP CLI
run: |
dpkg --print-architecture
curl -LJO https://tools.hana.ondemand.com/additional/btp-cli-linux-amd64-latest.tar.gz --cookie "eula_3_2_agreed=tools.hana.ondemand.com/developer-license-3_2.txt"
tar -xzf btp-cli-linux-amd64-latest.tar.gz
ls -a
mv linux-amd64/btp /usr/local/bin
chmod +x /usr/local/bin/btp

# Step 6: Install Multiapps Plugin
- name: Install Multiapps Plugin
run: |
cf add-plugin-repo CF-Community https://plugins.cloudfoundry.org
cf install-plugin multiapps -f

# Step 7: Login to CF
- name: Log in to Cloud Foundry
run: |
cf login -u ${{ secrets.CF_USERNAME }} -p ${{ secrets.CF_PASSWORD }} -o ${{ secrets.CF_ORG }} -s ${{ secrets.CF_SPACE }} -a ${{ secrets.CF_API }}

# Step 8: Build the project
- name: Build MTA Archive
run: |
cd deploy/cf
sed -i 's|{{BROKER_USER}}|'"${{ secrets.BROKER_USER }}"'|g' ./mtaext/ci.mtaext
sed -i 's|{{BROKER_PASSWORD}}|'"${{ secrets.BROKER_PASSWORD }}"'|g' ./mtaext/ci.mtaext
mbt build -e ./mtaext/ci.mtaext

# Step 9: Verify MTA Archive built successfully
- name: Deploy to CF
run: |
cf deploy ./deploy/cf/mta_archives/susaas_0.0.1.mtar -f

# Step 10: Verify MTA Archive built successfully
- name: Run Subscription Test Script
run: |
chmod +x ./code/test/subscription-test.sh
./code/test/subscription-test.sh
env:
BTP_USERNAME: ${{ secrets.CF_USERNAME }}
BTP_PASSWORD: ${{ secrets.CF_PASSWORD }}
BTP_SUBDOMAIN: ${{ secrets.BTP_SUBDOMAIN }}


38 changes: 35 additions & 3 deletions code/broker/start.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,12 +3,44 @@

import Broker from '@sap/sbf';

// If this is a CI CD deployment we get broker credentials from env and hardcode the catalog.
if (process.env.cicd) {
const catalog = `{
"services": [
{
"name": "susaas-api",
"description": "Sustainable SaaS API",
"bindable": true,
"plans": [
{
"name": "trial",
"description": "Trial Plan",
"id": "8f7c2dce-7500-4115-9df5-aebb9060e83d"
},
{
"name": "default",
"description": "Standard Plan",
"id": "d1d6bcc4-5f75-43cb-a537-3fddbff00f11"
},
{
"name": "premium",
"description": "Premium Plan",
"id": "2e12d1f4-d871-443c-8824-6f33d2748a1b"
}
],
"id": "ba609874-a1da-4f9c-a22b-f61de0c71a9e"
}
]
}`
let brokerConfig = { brokerCredentials: { [process.env["BROKER_USER"]]: process.env["BROKER_PASSWORD"] }, catalog: JSON.parse(catalog) }
new Broker(brokerConfig).start()
}
// If VCAP_APPLICATION is defined, we are in a Cloud Foundry scenario
// For local testing, the USER and PASSWORD are always injected via environment variables
if(process.env.VCAP_APPLICATION && process.env.NODE_ENV === "production"){
else if (process.env.VCAP_APPLICATION && process.env.NODE_ENV === "production" && process.env.cicd !== true) {
new Broker().start();
}else{
} else {
// In production Kyma scenarios and local testing, BROKER_USER and BROKER_PASSWORD are passed in env variables
let brokerConfig = { brokerCredentials : { [process.env["BROKER_USER"]] : process.env["BROKER_PASSWORD"] }}
let brokerConfig = { brokerCredentials: { [process.env["BROKER_USER"]]: process.env["BROKER_PASSWORD"] } }
new Broker(brokerConfig).start()
}
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ annotate service.CircularityMetrics with @(
},
{
$Type : 'UI.DataField',
Value : countryRecyclability,
Value : countryRecyclability_code,
![@UI.Importance] : #High
},
{
Expand Down Expand Up @@ -49,7 +49,7 @@ annotate service.CircularityMetrics with @(
AggregatableProperties : [{
Property : eoLRecyclability
}],
GroupableProperties : [countryRecyclability]
GroupableProperties : [countryRecyclability_code]
}
);

Expand All @@ -73,7 +73,7 @@ annotate service.CircularityMetrics with @(
UI.Chart #columnChartCircularityMetrics : {
ChartType : #Column,
Measures : [sumEoLRecyclability],
Dimensions : [countryRecyclability],
Dimensions : [countryRecyclability_code],
Title : '{i18n>chartCircularityMetrics}',
MeasureAttributes : [{
$Type : 'UI.ChartMeasureAttributeType',
Expand Down
6 changes: 3 additions & 3 deletions code/srv/srv/annotations/public/layouts_SalesSplits.cds
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,7 @@ annotate service.SalesSplits with @(
{
Property : reSellSales
}],
GroupableProperties : [ country],
GroupableProperties : [ country_code],
},
Analytics.AggregatedProperties : [
{
Expand Down Expand Up @@ -96,7 +96,7 @@ annotate service.SalesSplits with @(
},
{
$Type : 'UI.DataField',
Value : country,
Value : country_code,
![@UI.Importance] : #High
}
]}
Expand All @@ -107,7 +107,7 @@ annotate service.SalesSplits with @(
UI.Chart #columnChartSalesSplits : {
ChartType : #Column,
Measures : [sumTotalRevenue],
Dimensions : [country],
Dimensions : [country_code],
Title : '{i18n>chartSalesSplits}',
MeasureAttributes : [{
$Type : 'UI.ChartMeasureAttributeType',
Expand Down
200 changes: 200 additions & 0 deletions code/test/subscription-test.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,200 @@
#!/bin/bash

# Configuration Variables
SUBACCOUNT_GUID=""
APPLICATION_NAME="susaas-dev-tfe-saas-dev-test"
PLAN_NAME="default"
POLL_INTERVAL=10
TIMEOUT=90

# Login
btp_login() {
echo "Logging into BTP..."
btp login --url "https://cli.btp.cloud.sap" \
--user "$BTP_USERNAME" \
--password "$BTP_PASSWORD" \
--subdomain "$BTP_SUBDOMAIN"

if [[ $? -ne 0 ]]; then
echo "Error: BTP login failed."
exit 1
fi

echo "Successfully logged into BTP."
}

# Function to create a subaccount
create_subaccount() {
local START_TIME=$(date +%s)
local DISPLAY_NAME="ci-susaas-$START_TIME"
local REGION="eu10"
local SUBDOMAIN="ci-susaas-$START_TIME"
local START_TIME=$(date +%s)

RESPONSE=$(btp --format json create accounts/subaccount --display-name "$DISPLAY_NAME" --region "$REGION" --subdomain "$SUBDOMAIN")
SUBACCOUNT_GUID=$(echo "$RESPONSE" | jq -r '.guid')

if [[ -z "$SUBACCOUNT_GUID" ]]; then
echo "Error: Failed to create subaccount."
exit 1
fi

echo "Subaccount creation with GUID: $SUBACCOUNT_GUID"
}

# Function to check subaccount status
check_subaccount_status() {
local START_TIME=$(date +%s)

while true; do
local CURRENT_TIME=$(date +%s)
local ELAPSED_TIME=$(( CURRENT_TIME - START_TIME ))

if (( ELAPSED_TIME >= TIMEOUT )); then
echo "Error: Subaccount status check timed out after $TIMEOUT seconds."
exit 1
fi

RESPONSE=$(btp --format json get accounts/subaccount "$SUBACCOUNT_GUID")
STATUS=$(echo "$RESPONSE" | jq -r '.state')

if [[ "$STATUS" == "OK" ]]; then
echo "Subaccount is ready."
break
else
echo "Current status is $STATUS. Checking again in $POLL_INTERVAL seconds..."
fi

sleep "$POLL_INTERVAL"
done
}

# Function to subscribe to the application
subscribe_to_application() {
RESPONSE=$(btp --format json subscribe accounts/subaccount --to-app "$APPLICATION_NAME" --plan "$PLAN_NAME" -sa "$SUBACCOUNT_GUID")
JOB_ID=$(echo "$RESPONSE" | jq -r '.jobId')

if [[ -z "$JOB_ID" ]]; then
echo "Error: Failed to subscribe to the application."
exit 1
fi

echo "Subscription initiated with Job ID: $JOB_ID"
check_subscription_status
}

# Function to check subscription status
check_subscription_status() {
local START_TIME=$(date +%s)

while true; do
local CURRENT_TIME=$(date +%s)
local ELAPSED_TIME=$(( CURRENT_TIME - START_TIME ))

if (( ELAPSED_TIME >= TIMEOUT )); then
echo "Error: Subscription status check timed out after $TIMEOUT seconds."
exit 1
fi

RESPONSE=$(btp --format json get accounts/subscription -sa "$SUBACCOUNT_GUID" --of-app "$APPLICATION_NAME" --plan "$PLAN_NAME")
STATUS=$(echo "$RESPONSE" | jq -r '.state')

if [[ "$STATUS" == "SUBSCRIBED" ]]; then
echo "Successfully subscribed to the application."
break
elif [[ "$STATUS" == "ERROR" ]]; then
echo "Error: Subscription failed."
exit 1
else
echo "Current status is $STATUS. Checking again in $POLL_INTERVAL seconds..."
fi

sleep "$POLL_INTERVAL"
done
}

# Function to unsubscribe from the application
unsubscribe_from_application() {
echo "Initiating unsubscription from the application..."

RESPONSE=$(btp --format json unsubscribe accounts/subaccount --from-app "$APPLICATION_NAME" -sa "$SUBACCOUNT_GUID" --confirm)

# The unsubscribe process is asynchronous, so we don't have a job ID to check
check_unsubscribe_status
}

# Function to check unsubscription status
check_unsubscribe_status() {
local START_TIME=$(date +%s)

while true; do
local CURRENT_TIME=$(date +%s)
local ELAPSED_TIME=$(( CURRENT_TIME - START_TIME ))

if (( ELAPSED_TIME >= TIMEOUT )); then
echo "Error: Unsubscribe status check timed out after $TIMEOUT seconds."
exit 1
fi

RESPONSE=$(btp --format json get accounts/subscription -sa "$SUBACCOUNT_GUID" --of-app "$APPLICATION_NAME" --plan "$PLAN_NAME")
STATUS=$(echo "$RESPONSE" | jq -r '.state')

if [[ "$STATUS" == "NOT_SUBSCRIBED" ]]; then
echo "Successfully unsubscribed from the application."
break
elif [[ "$STATUS" == "ERROR" ]]; then
echo "Error: Unsubscription failed."
exit 1
else
echo "Current status is $STATUS. Checking again in $POLL_INTERVAL seconds..."
fi

sleep "$POLL_INTERVAL"
done
}
# Function to remove the subaccount
delete_subaccount() {
echo "Removing the subaccount..."

RESPONSE=$(btp --format json delete accounts/subaccount "$SUBACCOUNT_GUID" --confirm)

echo "Subaccount deletion initiated. Checking status..."

# Check the status of the subaccount deletion
check_subaccount_removal
}

# Function to check if the subaccount has been removed
check_subaccount_removal() {
local START_TIME=$(date +%s)

while true; do
local CURRENT_TIME=$(date +%s)
local ELAPSED_TIME=$(( CURRENT_TIME - START_TIME ))

if (( ELAPSED_TIME >= TIMEOUT )); then
echo "Error: Subaccount removal check timed out after $TIMEOUT seconds."
exit 1
fi

RESPONSE=$(btp --format json get accounts/subaccount "$SUBACCOUNT_GUID" 2>&1)

if echo "$RESPONSE" | grep -q "404 Not Found"; then
echo "Subaccount removed successfully."
break
else
echo "Subaccount still exists. Checking again in $POLL_INTERVAL seconds..."
fi

sleep "$POLL_INTERVAL"
done
}

# Main script execution
btp_login
create_subaccount
check_subaccount_status
subscribe_to_application
unsubscribe_from_application
delete_subaccount

Loading
Loading