BADGE é um sistema inovador destinado a autenticar e classificar conquistas por meio de badges digitais. Este sistema permite que empresas e instituições de ensino emitam badges para reconhecer e validar habilidades, realizações e progressos de indivíduos.
Após ler o passo a passo abaixo você pode executar a configuração/instalação automatizada, que fará a configuração do ambiente local e a criação dos recursos no Azure.
Windows 10 1709 (build 16299) ou posterior: Caso possua sistema Linux ou MacOS, ainda é possível instalar o BADGE, basta verificar quais passos abaixo se aplicam e adapta-los a sua necessidade.
Winget v1.6+: Siga o passo a passo indicado no site da Microsoft
PowerShell v7+: Certifique-se de ter o PowerShell v7 ou superior instalado. Para macOS e Linux, siga as instruções de instalação do PowerShell.
Conta no Azure: Crie uma conta gratuita no Azure. Todos os recursos do Azure utilizados foram configurados para usar o minimo de custos possível.
Azure CLI v2.56+: Todos os serviços do Azure serão instalados via CLI. Siga o passo a passo indicado no site da Microsoft para instalar ou atualizar.
Azure Functions Core Tools v3+: Siga o passo a passo indicado no site da Microsoft
Azure PowerShell v11.2+: Siga o passo a passo indicado no site da Microsoft
Install-Module -Name Az -AllowClobber -Scope CurrentUser
Logar no Azure via CLI: Todos os serviços do Azure serão instalados via CLI. Siga o passo a passo indicado no site da Microsoft.
Caso possua mais de uma subscription, selecione a desejada: Siga o passo a passo indicado no site da Microsoft
Configurar git: Siga o passo a passo indicado no site do git
Repo do Badges clonado: Siga o passo a passo indicado no site do git para clonar o repositorio https://github.com/arbgjr/BADGE.git.
Criar ou escolher um grupo de recursos no Azure para organização dos recursos que seão criados: Siga o passo a passo indicado no site da Microsoft. Guarde o nome da grupo de recursos criado.
Ex.:
$tagValue="Badge"
$randomIdentifier = Get-Random -Maximum 1000000
$resourceGroupName="rg-badges-$randomIdentifier"
$location="eastus2"
az group create --name $resourceGroupName --location "$location"
Ex.:
$storageAccountName="blob-badges-$randomIdentifier"
$skuStorage="Standard_LRS"
az storage account create --name $storageAccountName --location "$location" --resource-group $resourceGroupName --sku $skuStorage
Ex.:
$blobConnectionString = az storage account show-connection-string --name $storageaccountName --resource-group $resourceGroupName --query "connectionString" -o tsv
Ex.:
$BadgeContainerName="badges"
$FontsContainerName="fonts"
az storage container create --name $FontsContainerName --account-name $storageAccountName
az storage container create --name $BadgeContainerName --account-name $storageAccountName
Ex.:
$functionAppName="func-badges-$randomIdentifier"
$functionsVersion="4"
$pythonVersion="3.11"
az functionapp create --name $functionAppName --storage-account $storageAccountName --consumption-plan-location "$location" --resource-group $resourceGroupName --os-type Linux --runtime python --runtime-version $pythonVersion --functions-version $functionsVersion
Ex.:
az functionapp identity assign --name $functionAppName --resource-group $resourceGroupName
$AzFuncPrincipalId = $(az functionapp identity show --name $functionAppName --resource-group $resourceGroupName --query "principalId" -o tsv)
Ex.:
$nosqlDBName="nosql-badges-$randomIdentifier"
az cosmosdb create --name $nosqlDBName --resource-group $resourceGroupName --default-consistency-level Session --locations regionName="$location" failoverPriority=0 isZoneRedundant=False --kind MongoDB
Ex.:
$databaseName="dbBadges"
az cosmosdb mongodb database create --account-name $nosqlDBName --name $databaseName --resource-group $resourceGroupName
Ex.:
$keys = az cosmosdb keys list --name $nosqlDBName --resource-group $resourceGroupName --query "primaryMasterKey" -o tsv
$nosqlConnectionString = "mongodb://$nosqlDBName:`$keys@${nosqlDBName}.mongo.cosmos.azure.com:10255/?ssl=true&replicaSet=globaldb&retrywrites=false&maxIdleTimeMS=120000&appName=@${nosqlDBName}@"
Ex.:
$azappconfigName="appconfig-badges-$randomIdentifier"
az appconfig create --location "$location" --name $azappconfigName --resource-group $resourceGroupName
Ex.:
$appconfigConnectionString = az appconfig credential list --name $appconfigName --resource-group $resourceGroupName --query "[0].connectionString" -o tsv
Ex.:
az role assignment create --assignee $AzFuncPrincipalId --role "Contributor" --scope (az appconfig show --name $azAppConfigName --resource-group $resourceGroupName --query "id" -o tsv)
Ex.:
$keyVaultName = "kv-badges-$randomIdentifier"
az keyvault create --name $keyVaultName --resource-group $resourceGroupName --location $location
$AzKVUri = "https://$keyVaultName.vault.azure.net/"
Ex.:
az keyvault set-policy --name $keyVaultName --object-id $AzFuncPrincipalId --secret-permissions get list set delete --key-permissions get create delete list update --certificate-permissions get list update create delete
Ex.:
$appSettings = Get-AzWebApp -ResourceGroupName $resourceGroupName -Name $functionAppName
$connectionStringName = "AppConfigConnectionString"
$appSettings.SiteConfig.ConnectionStrings.Add((New-Object Microsoft.Azure.Management.WebSites.Models.ConnectionStringInfo -ArgumentList $connectionStringName, $appconfigConnectionString, "Custom"))
Set-AzWebApp -ResourceGroupName $resourceGroupName -Name $functionAppName -AppSettings $appSettings.SiteConfig.AppSettings
Ex.:
az storage blob upload --container-name $BadgeContainerName --file "CaminhoDoTemplateDoBadge\template_badge.png" --name "template_badge.png" --account-name $storageAccountName
Baixar as fontes abaixo, e descompactar os arquivos baixados:
Fazer upload dos arquivos para o blob storage: Considero que o comando abaixo está sendo executado de dentro da pasta local do repo do BADGE
Ex.:
$blobUploadParameters = @(
@{ContainerName=$BadgeContainerName; LocalFilePath="CaminhoDoTemplateDoBadge\template_badge.png"; BlobName="template_badge.png"},
@{ContainerName=$BadgeContainerName; LocalFilePath=".\badge_data.schema.json"; BlobName="badge_data.schema.json"},
@{ContainerName=$FontsContainerName; LocalFilePath="CaminhoDaFonteNotoColorEmoji\NotoColorEmoji-Regular.ttf"; BlobName="NotoColorEmoji-Regular.ttf"},
@{ContainerName=$FontsContainerName; LocalFilePath="CaminhoDaFonteRubikBold\Rubik-Bold.ttf"; BlobName="Rubik-Bold.ttf"},
@{ContainerName=$FontsContainerName; LocalFilePath="CaminhoDaFonteRubikRegular\Rubik-Regular.ttf"; BlobName="Rubik-Regular.ttf"}
)
$blobUploadParameters | ForEach-Object {
az storage blob upload --container-name $_.ContainerName --file $_.LocalFilePath --name $_.BlobName --account-name $storageAccountName
}
Ex.:
$blobFiles = @(
@{ContainerName=$BadgeContainerName; BlobName='template_badge.png'; BlobUrlVariableName='blobUrlTemplateBadge'},
@{ContainerName=$BadgeContainerName; BlobName='badge_data.schema.json'; BlobUrlVariableName='BadgeDBSchemaURL'},
@{ContainerName=$FontsContainerName; BlobName='NotoColorEmoji-Regular.ttf'; BlobUrlVariableName='blobUrlNotoColorEmoji'},
@{ContainerName=$FontsContainerName; BlobName='Rubik-Bold.ttf'; BlobUrlVariableName='blobUrlRubikBold'},
@{ContainerName=$FontsContainerName; BlobName='Rubik-Regular.ttf'; BlobUrlVariableName='blobUrlRubikRegular'}
)
$blobFiles | ForEach-Object {
$expiryDate = (Get-Date -Year (Get-Date).Year -Month 12 -Day 31 -Hour 23 -Minute 59 -Second 59).ToUniversalTime().ToString("yyyy-MM-ddTHH:mm:ssZ")
$sasToken = az storage blob generate-sas --container-name $_.ContainerName --name $_.BlobName --permissions r --expiry $expiryDate --account-name $storageAccountName --https-only --output tsv
Set-Variable -Name $_.BlobUrlVariableName -Value ("https://$storageAccountName.blob.core.windows.net/$($_.ContainerName)/$($_.BlobName)?$sasToken")
}
Ex.:
$issuerName="Acme Industries"
$areaName="AsPoNe"
$arquivosEValores = @(
@{Caminho=".\BadgeHeaderInfo.json"; ValorAntigo="<blobUrlRubikRegular>"; ValorNovo=$blobUrlRubikRegular},
@{Caminho=".\template.json"; ValorAntigo="<issuerName>"; ValorNovo=$issuerName},
@{Caminho=".\template.json"; ValorAntigo="<areaName>"; ValorNovo=$areaName},
@{Caminho=".\template.json"; ValorAntigo="<blobUrlRubikBold>"; ValorNovo=$blobUrlRubikBold},
@{Caminho=".\template.json"; ValorAntigo="<blobUrlNotoColorEmoji>"; ValorNovo=$blobUrlNotoColorEmoji}
)
$arquivosEValores | ForEach-Object {
$conteudoDoArquivo = Get-Content -Path $_.Caminho -Raw
$conteudoDoArquivoAtualizado = $conteudoDoArquivo -replace $_.ValorAntigo, $_.ValorNovo
Set-Content -Path $_.Caminho -Value $conteudoDoArquivoAtualizado
}
Ex.:
$BadgeVerificationUrl="https://www.qualquerurl.com"
$LinkedInPost=""Estou muito feliz em compartilhar que acabei de conquistar um novo badge: {badge_name}!\r\nEsta conquista representa {additional_info}.\r\nVocê pode verificar a autenticidade do meu badge aqui: {validation_url}\r\n#Conquista #Badge #DesenvolvimentoProfissional"
$newSettings = @(
@{name='AzKVURI'; value=$AzKVURI},
@{name='BadgeContainerName'; value=$BadgeContainerName},
@{name='BadgeDBSchemaURL'; value=$BadgeDBSchemaURL},
@{name='BadgeVerificationUrl'; value=$BadgeVerificationUrl},
@{name='LinkedInPost'; value=$LinkedInPost}
)
$newSettings | ForEach-Object {Set-AppConfigKeyValue -azAppConfigName $azappconfigName -settingName $_.name -settingValue $_.value -ContentType "text/plain;charset=utf-8" -tag $tagValue}
$contentBadgeHeaderInfo = Get-Content -Path ".\BadgeHeaderInfo.json" -Raw
az appconfig kv set --name $azappconfigName --key BadgeHeaderInfo --value $content --content-type "application/json" --label $tagValue
Ex.:
$keyVaultSecretParameters = @(
@{SecretName="BlobConnectionString"; SecretValue=$blobConnectionString; ContentType="text/plain; charset=utf-8"},
@{SecretName="CosmosDBConnectionString"; SecretValue=$nosqlConnectionString; ContentType="text/plain; charset=utf-8"}
)
$keyVaultSecretParameters | ForEach-Object {
az keyvault secret set --vault-name $keyVaultName --name $_.SecretName --value $_.SecretValue --content-type $_.ContentType
}
Ex.:
$verb = "POST"
$resourceType = "docs"
$resourceLink = "dbs/$databaseName/colls/Templates"
$resourceKey = $keys # Chave primária do Cosmos DB
$date = [DateTime]::UtcNow.ToString("R")
$keyBytes = [System.Text.Encoding]::UTF8.GetBytes($resourceKey)
$hashAlgorithm = [System.Security.Cryptography.HMACSHA256]::new($keyBytes)
$stringToSign = $verb.ToLower() + "`n" + $resourceType.ToLower() + "`n" + $resourceLink + "`n" + $date.ToLower() + "`n" + "" + "`n"
$signatureBytes = $hashAlgorithm.ComputeHash([System.Text.Encoding]::UTF8.GetBytes($stringToSign))
$signature = [Convert]::ToBase64String($signatureBytes)
$authHeader = @{
Authorization=("type=master&ver=1.0&sig=" + $signature)
"x-ms-date"=$date
}
$uriCosmosDB = "https://$nosqlDBName.documents.azure.com:443/dbs/$databaseName/colls/Templates/docs"
$arquivoJson = ".\template.json"
$conteudoJson = Get-Content -Path $arquivoJson -Raw
$response = Invoke-RestMethod -Method Post -Uri $uriCosmosDB -Body $conteudoJson -Headers $authHeader -ContentType "application/json"
$response
Após instalar os pré-requisitos basta seguir os passos abaixo:
Abrir PowerShell como Administrador: Clique com o botão direito no menu Iniciar e selecione "Windows PowerShell (Admin)".
Baixe o script com o comando:
curl -L -o install.ps1 https://raw.githubusercontent.com/arbgjr/BADGE/main/install.ps1
Edite o arquivo install.ps1 onde estiver indicado.
Execute o script abaixo é siga as instruções na tela:
.\install.ps1
Contribuições são bem-vindas! Para contribuir, siga as diretrizes de contribuição no repositório. E sempre siga nosso código de conduta.
Vide LICENSE.