Compare commits
No commits in common. "public" and "v25.9.17" have entirely different histories.
|
@ -1,26 +0,0 @@
|
||||||
name: "Get Build Options"
|
|
||||||
description: "Sanitizies and unifies the environment into build options"
|
|
||||||
outputs:
|
|
||||||
short-sha:
|
|
||||||
description: "Shortened hash if the current commit"
|
|
||||||
build-arch:
|
|
||||||
description: "Docker-compatible representation of build arch"
|
|
||||||
build-platform:
|
|
||||||
description: "Docker-compatible representation of build platform"
|
|
||||||
runs:
|
|
||||||
using: "composite"
|
|
||||||
steps:
|
|
||||||
- name: "Compute Build Options"
|
|
||||||
shell: "bash"
|
|
||||||
run: |
|
|
||||||
set -x
|
|
||||||
SHORT_SHA="${GITHUB_SHA::8}"
|
|
||||||
BUILD_ARCH="amd64"
|
|
||||||
BUILD_PLATFORM="linux/amd64"
|
|
||||||
if [ "${RUNNER_ARCH}" = "ARM64" ];then
|
|
||||||
BUILD_ARCH="arm64"
|
|
||||||
BUILD_PLATFORM="linux/arm64"
|
|
||||||
fi
|
|
||||||
echo "short-sha=$SHORT_SHA" >> $GITHUB_OUTPUT
|
|
||||||
echo "build-arch=$BUILD_ARCH" >> $GITHUB_OUTPUT
|
|
||||||
echo "build-platform=$BUILD_PLATFORM" >> $GITHUB_OUTPUT
|
|
|
@ -1,17 +0,0 @@
|
||||||
name: "Get Run Info"
|
|
||||||
description: "Sanitizies and unifies the environment into run info"
|
|
||||||
inputs:
|
|
||||||
compose-project-base:
|
|
||||||
description: "Base for the Compose project"
|
|
||||||
required: true
|
|
||||||
outputs:
|
|
||||||
compose-project:
|
|
||||||
description: "Compose project name"
|
|
||||||
runs:
|
|
||||||
using: "composite"
|
|
||||||
steps:
|
|
||||||
- name: "Compute Run Info"
|
|
||||||
shell: "bash"
|
|
||||||
run: |
|
|
||||||
set -x
|
|
||||||
echo "compose-project=${{ inputs.compose-project-base }}-${GITHUB_RUN_NUMBER}" >> $GITHUB_OUTPUT
|
|
|
@ -1,27 +0,0 @@
|
||||||
name: "Get Run Info"
|
|
||||||
description: "Sanitizies and unifies the environment into run info"
|
|
||||||
inputs:
|
|
||||||
service:
|
|
||||||
description: "The service to work on"
|
|
||||||
required: true
|
|
||||||
outputs:
|
|
||||||
version:
|
|
||||||
description: "Service version"
|
|
||||||
build-number:
|
|
||||||
description: "Build number"
|
|
||||||
runs:
|
|
||||||
using: "composite"
|
|
||||||
steps:
|
|
||||||
- name: "Compute Service Version"
|
|
||||||
shell: "bash"
|
|
||||||
run: |
|
|
||||||
set -x
|
|
||||||
if [[ ! -z "${GITHUB_HEAD_REF}" || "${GITHUB_REF_NAME}" = "development" ]]; then
|
|
||||||
VERSION="${GITHUB_SHA::8}"
|
|
||||||
BUILD="${GITHUB_RUN_NUMBER}"
|
|
||||||
else
|
|
||||||
VERSION="v$(grep -Po '(?<=^version\s=\s")[^"]+' services/${{ inputs.service }}/pyproject.toml)"
|
|
||||||
BUILD="01"
|
|
||||||
fi
|
|
||||||
echo "version=$VERSION" >> $GITHUB_OUTPUT
|
|
||||||
echo "build-number=$BUILD" >> $GITHUB_OUTPUT
|
|
|
@ -1,32 +0,0 @@
|
||||||
name: "Set up k8s"
|
|
||||||
description: "Downloads and installs k8s tools"
|
|
||||||
inputs:
|
|
||||||
arch:
|
|
||||||
description: "Architecture"
|
|
||||||
required: true
|
|
||||||
kubectl-version:
|
|
||||||
description: "kubectl version to install"
|
|
||||||
required: false
|
|
||||||
default: "1.33.4"
|
|
||||||
kustomize-version:
|
|
||||||
description: "kustomize version to install"
|
|
||||||
required: false
|
|
||||||
default: "5.7.1"
|
|
||||||
runs:
|
|
||||||
using: "composite"
|
|
||||||
steps:
|
|
||||||
- name: "Install k8s tools"
|
|
||||||
shell: "bash"
|
|
||||||
run: |
|
|
||||||
set -x
|
|
||||||
mkdir -p /opt/k8s/bin /opt/k8s/etc /opt/k8s/src
|
|
||||||
|
|
||||||
wget -O /opt/k8s/src/kubectl "https://nexus.bthlabs.pl/repository/ops-tools/k8s/kubectl-${{ inputs.kubectl-version }}-linux-${{ inputs.arch }}"
|
|
||||||
chmod a+x /opt/k8s/src/kubectl
|
|
||||||
mv /opt/k8s/src/kubectl /opt/k8s/bin
|
|
||||||
|
|
||||||
wget -O /opt/k8s/src/kustomize "https://nexus.bthlabs.pl/repository/ops-tools/k8s/kustomize-${{ inputs.kustomize-version }}-linux-${{ inputs.arch }}"
|
|
||||||
chmod a+x /opt/k8s/src/kustomize
|
|
||||||
mv /opt/k8s/src/kustomize /opt/k8s/bin
|
|
||||||
|
|
||||||
rm -rf /opt/k8s/src/
|
|
|
@ -1,28 +0,0 @@
|
||||||
#!/usr/bin/env bash
|
|
||||||
set -e
|
|
||||||
set +x
|
|
||||||
set -o pipefail
|
|
||||||
|
|
||||||
cat >"./docker-compose-ci-${COMPOSE_PROJECT}.yaml" <<EOF
|
|
||||||
services:
|
|
||||||
postgres:
|
|
||||||
image: "docker-hosted.nexus.bthlabs.pl/hotpocket/postgres:15.13-${COMPOSE_PROJECT}"
|
|
||||||
|
|
||||||
keycloak:
|
|
||||||
image: "docker-hosted.nexus.bthlabs.pl/hotpocket/keycloak:22.0.3-${COMPOSE_PROJECT}"
|
|
||||||
|
|
||||||
rabbitmq:
|
|
||||||
image: "docker-hosted.nexus.bthlabs.pl/hotpocket/rabbitmq:3.10.8-${COMPOSE_PROJECT}"
|
|
||||||
|
|
||||||
apple-ci:
|
|
||||||
image: "docker-hosted.nexus.bthlabs.pl/hotpocket/apple:ci-${COMPOSE_PROJECT}"
|
|
||||||
|
|
||||||
backend-ci:
|
|
||||||
image: "docker-hosted.nexus.bthlabs.pl/hotpocket/backend:ci-${COMPOSE_PROJECT}"
|
|
||||||
|
|
||||||
extension-ci:
|
|
||||||
image: "docker-hosted.nexus.bthlabs.pl/hotpocket/extension:ci-${COMPOSE_PROJECT}"
|
|
||||||
|
|
||||||
packages-ci:
|
|
||||||
image: "docker-hosted.nexus.bthlabs.pl/hotpocket/packages:ci-${COMPOSE_PROJECT}"
|
|
||||||
EOF
|
|
|
@ -17,24 +17,8 @@ jobs:
|
||||||
steps:
|
steps:
|
||||||
- name: "Checkout the code"
|
- name: "Checkout the code"
|
||||||
uses: "actions/checkout@v2"
|
uses: "actions/checkout@v2"
|
||||||
- name: "Get run info"
|
|
||||||
id: "get-run-info"
|
|
||||||
uses: "./.gitea/actions/get-run-info"
|
|
||||||
with:
|
|
||||||
compose-project-base: "${{ vars.COMPOSE_PROJECT_BASE }}"
|
|
||||||
- name: "Get build options"
|
|
||||||
id: "get-build-options"
|
|
||||||
uses: "./.gitea/actions/get-build-options"
|
|
||||||
- name: "Set up Docker Buildx"
|
- name: "Set up Docker Buildx"
|
||||||
id: "setup-docker-buildx"
|
|
||||||
uses: "docker/setup-buildx-action@v3"
|
uses: "docker/setup-buildx-action@v3"
|
||||||
with:
|
|
||||||
driver: "remote"
|
|
||||||
endpoint: "tcp://builder-01.bthlab:2375"
|
|
||||||
platforms: "linux/amd64"
|
|
||||||
append: |
|
|
||||||
- endpoint: "tcp://builder-mac-01.bthlab:2375"
|
|
||||||
platforms: "linux/arm64"
|
|
||||||
- name: "Build `postgres` image"
|
- name: "Build `postgres` image"
|
||||||
uses: docker/build-push-action@v6
|
uses: docker/build-push-action@v6
|
||||||
with:
|
with:
|
||||||
|
@ -42,10 +26,7 @@ jobs:
|
||||||
context: "services/"
|
context: "services/"
|
||||||
push: false
|
push: false
|
||||||
load: true
|
load: true
|
||||||
tags: "docker-hosted.nexus.bthlabs.pl/hotpocket/postgres:15.13-${{ steps.get-run-info.outputs.compose-project }}"
|
tags: "docker-hosted.nexus.bthlabs.pl/hotpocket/postgres:15.13-local"
|
||||||
platforms: "${{ steps.get-build-options.outputs.build-platform }}"
|
|
||||||
cache-from: "type=registry,ref=nexus.bthlab.bthlabs.net:8001/hotpocket"
|
|
||||||
cache-to: "type=registry,ref=nexus.bthlab.bthlabs.net:8001/hotpocket,mode=max"
|
|
||||||
- name: "Build `keycloak` image"
|
- name: "Build `keycloak` image"
|
||||||
uses: docker/build-push-action@v6
|
uses: docker/build-push-action@v6
|
||||||
with:
|
with:
|
||||||
|
@ -53,10 +34,7 @@ jobs:
|
||||||
context: "services/"
|
context: "services/"
|
||||||
push: false
|
push: false
|
||||||
load: true
|
load: true
|
||||||
tags: "docker-hosted.nexus.bthlabs.pl/hotpocket/keycloak:22.0.3-${{ steps.get-run-info.outputs.compose-project }}"
|
tags: "docker-hosted.nexus.bthlabs.pl/hotpocket/keycloak:22.0.3-local"
|
||||||
platforms: "${{ steps.get-build-options.outputs.build-platform }}"
|
|
||||||
cache-from: "type=registry,ref=nexus.bthlab.bthlabs.net:8001/hotpocket"
|
|
||||||
cache-to: "type=registry,ref=nexus.bthlab.bthlabs.net:8001/hotpocket,mode=max"
|
|
||||||
- name: "Build `rabbitmq` image"
|
- name: "Build `rabbitmq` image"
|
||||||
uses: docker/build-push-action@v6
|
uses: docker/build-push-action@v6
|
||||||
with:
|
with:
|
||||||
|
@ -64,10 +42,7 @@ jobs:
|
||||||
context: "services/"
|
context: "services/"
|
||||||
push: false
|
push: false
|
||||||
load: true
|
load: true
|
||||||
tags: "docker-hosted.nexus.bthlabs.pl/hotpocket/rabbitmq:3.10.8-${{ steps.get-run-info.outputs.compose-project }}"
|
tags: "docker-hosted.nexus.bthlabs.pl/hotpocket/rabbitmq:3.10.8-local"
|
||||||
platforms: "${{ steps.get-build-options.outputs.build-platform }}"
|
|
||||||
cache-from: "type=registry,ref=nexus.bthlab.bthlabs.net:8001/hotpocket"
|
|
||||||
cache-to: "type=registry,ref=nexus.bthlab.bthlabs.net:8001/hotpocket,mode=max"
|
|
||||||
- name: "Build `backend-ci` image"
|
- name: "Build `backend-ci` image"
|
||||||
uses: docker/build-push-action@v6
|
uses: docker/build-push-action@v6
|
||||||
with:
|
with:
|
||||||
|
@ -76,10 +51,7 @@ jobs:
|
||||||
target: "ci"
|
target: "ci"
|
||||||
push: false
|
push: false
|
||||||
load: true
|
load: true
|
||||||
tags: "docker-hosted.nexus.bthlabs.pl/hotpocket/backend:ci-${{ steps.get-run-info.outputs.compose-project }}"
|
tags: "docker-hosted.nexus.bthlabs.pl/hotpocket/backend:ci-local"
|
||||||
platforms: "${{ steps.get-build-options.outputs.build-platform }}"
|
|
||||||
cache-from: "type=registry,ref=nexus.bthlab.bthlabs.net:8001/hotpocket"
|
|
||||||
cache-to: "type=registry,ref=nexus.bthlab.bthlabs.net:8001/hotpocket,mode=max"
|
|
||||||
- name: "Build `packages-ci` image"
|
- name: "Build `packages-ci` image"
|
||||||
uses: docker/build-push-action@v6
|
uses: docker/build-push-action@v6
|
||||||
with:
|
with:
|
||||||
|
@ -88,10 +60,7 @@ jobs:
|
||||||
target: "ci"
|
target: "ci"
|
||||||
push: false
|
push: false
|
||||||
load: true
|
load: true
|
||||||
tags: "docker-hosted.nexus.bthlabs.pl/hotpocket/packages:ci-${{ steps.get-run-info.outputs.compose-project }}"
|
tags: "docker-hosted.nexus.bthlabs.pl/hotpocket/packages:ci-local"
|
||||||
platforms: "${{ steps.get-build-options.outputs.build-platform }}"
|
|
||||||
cache-from: "type=registry,ref=nexus.bthlab.bthlabs.net:8001/hotpocket"
|
|
||||||
cache-to: "type=registry,ref=nexus.bthlab.bthlabs.net:8001/hotpocket,mode=max"
|
|
||||||
- name: "Build `extension-ci` image"
|
- name: "Build `extension-ci` image"
|
||||||
uses: docker/build-push-action@v6
|
uses: docker/build-push-action@v6
|
||||||
with:
|
with:
|
||||||
|
@ -100,91 +69,23 @@ jobs:
|
||||||
target: "ci"
|
target: "ci"
|
||||||
push: false
|
push: false
|
||||||
load: true
|
load: true
|
||||||
tags: "docker-hosted.nexus.bthlabs.pl/hotpocket/extension:ci-${{ steps.get-run-info.outputs.compose-project }}"
|
tags: "docker-hosted.nexus.bthlabs.pl/hotpocket/extension:ci-local"
|
||||||
platforms: "${{ steps.get-build-options.outputs.build-platform }}"
|
|
||||||
cache-from: "type=registry,ref=nexus.bthlab.bthlabs.net:8001/hotpocket"
|
|
||||||
cache-to: "type=registry,ref=nexus.bthlab.bthlabs.net:8001/hotpocket,mode=max"
|
|
||||||
- name: "Build `apple-ci` image"
|
|
||||||
uses: docker/build-push-action@v6
|
|
||||||
with:
|
|
||||||
file: "services/apple/Dockerfile"
|
|
||||||
context: "services/"
|
|
||||||
target: "ci"
|
|
||||||
push: false
|
|
||||||
load: true
|
|
||||||
tags: "docker-hosted.nexus.bthlabs.pl/hotpocket/apple:ci-${{ steps.get-run-info.outputs.compose-project }}"
|
|
||||||
platforms: "${{ steps.get-build-options.outputs.build-platform }}"
|
|
||||||
cache-from: "type=registry,ref=nexus.bthlab.bthlabs.net:8001/hotpocket"
|
|
||||||
cache-to: "type=registry,ref=nexus.bthlab.bthlabs.net:8001/hotpocket,mode=max"
|
|
||||||
- name: "Prepare the build"
|
|
||||||
id: "prepare"
|
|
||||||
env:
|
|
||||||
COMPOSE_PROJECT: "${{ steps.get-run-info.outputs.compose-project }}"
|
|
||||||
run: |
|
|
||||||
set -x
|
|
||||||
./.gitea/tools/render-docker-compose-ci.sh
|
|
||||||
- name: "Run `backend` checks"
|
- name: "Run `backend` checks"
|
||||||
if: "steps.prepare.conclusion == 'success'"
|
|
||||||
env:
|
|
||||||
COMPOSE_PROJECT: "${{ steps.get-run-info.outputs.compose-project }}"
|
|
||||||
run: |
|
run: |
|
||||||
set -x
|
set -x
|
||||||
docker compose \
|
docker compose -f docker-compose.yaml -f docker-compose-ci.yaml run --rm backend-ci inv ci
|
||||||
-p "${COMPOSE_PROJECT}" \
|
|
||||||
-f "docker-compose.yaml" \
|
|
||||||
-f "docker-compose-ci.yaml" \
|
|
||||||
-f "docker-compose-ci-${COMPOSE_PROJECT}.yaml" \
|
|
||||||
run --rm \
|
|
||||||
backend-ci inv ci
|
|
||||||
- name: "Run `packages` checks"
|
- name: "Run `packages` checks"
|
||||||
if: "steps.prepare.conclusion == 'success'"
|
if: always()
|
||||||
env:
|
|
||||||
COMPOSE_PROJECT: "${{ steps.get-run-info.outputs.compose-project }}"
|
|
||||||
run: |
|
run: |
|
||||||
set -x
|
set -x
|
||||||
docker compose \
|
docker compose -f docker-compose.yaml -f docker-compose-ci.yaml run --rm packages-ci inv ci
|
||||||
-p "${COMPOSE_PROJECT}" \
|
|
||||||
-f "docker-compose.yaml" \
|
|
||||||
-f "docker-compose-ci.yaml" \
|
|
||||||
-f "docker-compose-ci-${COMPOSE_PROJECT}.yaml" \
|
|
||||||
run --rm \
|
|
||||||
packages-ci inv ci
|
|
||||||
- name: "Run `extension` checks"
|
- name: "Run `extension` checks"
|
||||||
if: "steps.prepare.conclusion == 'success'"
|
if: always()
|
||||||
env:
|
|
||||||
COMPOSE_PROJECT: "${{ steps.get-run-info.outputs.compose-project }}"
|
|
||||||
run: |
|
run: |
|
||||||
set -x
|
set -x
|
||||||
docker compose \
|
docker compose -f docker-compose.yaml -f docker-compose-ci.yaml run --rm extension-ci inv ci
|
||||||
-p "${COMPOSE_PROJECT}" \
|
|
||||||
-f "docker-compose.yaml" \
|
|
||||||
-f "docker-compose-ci.yaml" \
|
|
||||||
-f "docker-compose-ci-${COMPOSE_PROJECT}.yaml" \
|
|
||||||
run --rm \
|
|
||||||
extension-ci inv ci
|
|
||||||
- name: "Run `apple` checks"
|
|
||||||
if: "steps.prepare.conclusion == 'success'"
|
|
||||||
env:
|
|
||||||
COMPOSE_PROJECT: "${{ steps.get-run-info.outputs.compose-project }}"
|
|
||||||
run: |
|
|
||||||
set -x
|
|
||||||
docker compose \
|
|
||||||
-p "${COMPOSE_PROJECT}" \
|
|
||||||
-f "docker-compose.yaml" \
|
|
||||||
-f "docker-compose-ci.yaml" \
|
|
||||||
-f "docker-compose-ci-${COMPOSE_PROJECT}.yaml" \
|
|
||||||
run --rm \
|
|
||||||
apple-ci inv ci
|
|
||||||
- name: "Clean up"
|
- name: "Clean up"
|
||||||
if: always()
|
if: always()
|
||||||
env:
|
|
||||||
COMPOSE_PROJECT: "${{ steps.get-run-info.outputs.compose-project }}"
|
|
||||||
run: |
|
run: |
|
||||||
set -x
|
set -x
|
||||||
docker compose \
|
docker compose -f docker-compose.yaml -f docker-compose-ci.yaml down --volumes
|
||||||
-p "${COMPOSE_PROJECT}" \
|
|
||||||
-f "docker-compose.yaml" \
|
|
||||||
-f "docker-compose-ci.yaml" \
|
|
||||||
-f "docker-compose-ci-${COMPOSE_PROJECT}.yaml" \
|
|
||||||
down --volumes --rmi all || true
|
|
||||||
rm -f "docker-compose-ci-${COMPOSE_PROJECT}.yaml" || true
|
|
||||||
|
|
|
@ -1,163 +0,0 @@
|
||||||
name: "Deploy to development"
|
|
||||||
|
|
||||||
on:
|
|
||||||
push:
|
|
||||||
branches:
|
|
||||||
- "development"
|
|
||||||
|
|
||||||
jobs:
|
|
||||||
build-deployment-images:
|
|
||||||
name: "Build deployment images"
|
|
||||||
runs-on: "ubuntu-latest"
|
|
||||||
steps:
|
|
||||||
- name: "Checkout the code"
|
|
||||||
uses: "actions/checkout@v2"
|
|
||||||
- name: "Get build options"
|
|
||||||
id: "get-build-options"
|
|
||||||
uses: "./.gitea/actions/get-build-options"
|
|
||||||
- name: "Get `backend` version"
|
|
||||||
id: "get-backend-version"
|
|
||||||
uses: "./.gitea/actions/get-service-version"
|
|
||||||
with:
|
|
||||||
service: "backend"
|
|
||||||
- name: "Import Secrets"
|
|
||||||
id: "import-secrets"
|
|
||||||
uses: "hashicorp/vault-action@v2"
|
|
||||||
with:
|
|
||||||
url: "https://vault.bthlabs.pl/"
|
|
||||||
method: "approle"
|
|
||||||
roleId: "${{ secrets.VAULT_ROLE_ID }}"
|
|
||||||
secretId: "${{ secrets.VAULT_SECRET_ID }}"
|
|
||||||
secrets: |
|
|
||||||
gitea/data/docker-hosted.nexus.bthlabs.pl username | DOCKER_USERNAME ;
|
|
||||||
gitea/data/docker-hosted.nexus.bthlabs.pl password | DOCKER_PASSWORD
|
|
||||||
- name: "Set up Docker Buildx"
|
|
||||||
id: "setup-docker-buildx"
|
|
||||||
uses: "docker/setup-buildx-action@v3"
|
|
||||||
with:
|
|
||||||
driver: "remote"
|
|
||||||
endpoint: "tcp://builder-01.bthlab:2375"
|
|
||||||
platforms: "linux/amd64"
|
|
||||||
append: |
|
|
||||||
- endpoint: "tcp://builder-mac-01.bthlab:2375"
|
|
||||||
platforms: "linux/arm64"
|
|
||||||
- name: "Login to Docket Registry"
|
|
||||||
uses: "docker/login-action@v3"
|
|
||||||
with:
|
|
||||||
registry: "docker-hosted.nexus.bthlabs.pl"
|
|
||||||
username: "${{ steps.import-secrets.outputs.DOCKER_USERNAME }}"
|
|
||||||
password: "${{ steps.import-secrets.outputs.DOCKER_PASSWORD }}"
|
|
||||||
- name: "Build `backend-deployment` image"
|
|
||||||
env:
|
|
||||||
SHORT_SHA: "${{ steps.get-build-options.outputs.short-sha }}"
|
|
||||||
VERSION: "${{ steps.get-backend-version.outputs.version }}"
|
|
||||||
BUILD: "${{ steps.get-backend-version.outputs.build-number }}"
|
|
||||||
run: |
|
|
||||||
set -x
|
|
||||||
docker buildx build \
|
|
||||||
--cache-from "type=registry,ref=nexus.bthlab.bthlabs.net:8001/hotpocket" \
|
|
||||||
--cache-to "type=registry,ref=nexus.bthlab.bthlabs.net:8001/hotpocket,mode=max" \
|
|
||||||
--push \
|
|
||||||
--platform linux/amd64,linux/arm64 \
|
|
||||||
--build-arg IMAGE_ID="deployment.${SHORT_SHA}" \
|
|
||||||
-f services/backend/Dockerfile \
|
|
||||||
--target deployment \
|
|
||||||
-t "docker-hosted.nexus.bthlabs.pl/hotpocket/backend:deployment-${VERSION}-${BUILD}" \
|
|
||||||
services/
|
|
||||||
- name: "Build `backend-aio` image"
|
|
||||||
env:
|
|
||||||
SHORT_SHA: "${{ steps.get-build-options.outputs.short-sha }}"
|
|
||||||
VERSION: "${{ steps.get-backend-version.outputs.version }}"
|
|
||||||
BUILD: "${{ steps.get-backend-version.outputs.build-number }}"
|
|
||||||
run: |
|
|
||||||
set -x
|
|
||||||
docker buildx build \
|
|
||||||
--cache-from "type=registry,ref=nexus.bthlab.bthlabs.net:8001/hotpocket" \
|
|
||||||
--cache-to "type=registry,ref=nexus.bthlab.bthlabs.net:8001/hotpocket,mode=max" \
|
|
||||||
--push \
|
|
||||||
--platform linux/amd64,linux/arm64 \
|
|
||||||
--build-arg IMAGE_ID="aio.${SHORT_SHA}" \
|
|
||||||
-f services/backend/Dockerfile \
|
|
||||||
--target aio \
|
|
||||||
-t "docker-hosted.nexus.bthlabs.pl/hotpocket/backend:aio-${VERSION}-${BUILD}" \
|
|
||||||
services/
|
|
||||||
|
|
||||||
deploy:
|
|
||||||
name: "Deploy"
|
|
||||||
runs-on: "ubuntu-latest"
|
|
||||||
needs:
|
|
||||||
- "build-deployment-images"
|
|
||||||
env:
|
|
||||||
KUBERNETES_NAMESPACE: "hotpocket-development"
|
|
||||||
KUBERNETES_CLUSTER: "k8s.bthlab"
|
|
||||||
steps:
|
|
||||||
- name: "Checkout the code"
|
|
||||||
uses: "actions/checkout@v2"
|
|
||||||
- name: "Get run info"
|
|
||||||
id: "get-run-info"
|
|
||||||
uses: "./.gitea/actions/get-run-info"
|
|
||||||
with:
|
|
||||||
compose-project-base: "${{ vars.COMPOSE_PROJECT_BASE }}"
|
|
||||||
- name: "Get build options"
|
|
||||||
id: "get-build-options"
|
|
||||||
uses: "./.gitea/actions/get-build-options"
|
|
||||||
- name: "Get `backend` version"
|
|
||||||
id: "get-backend-version"
|
|
||||||
uses: "./.gitea/actions/get-service-version"
|
|
||||||
with:
|
|
||||||
service: "backend"
|
|
||||||
- name: "Setup k8s"
|
|
||||||
uses: "./.gitea/actions/setup-k8s"
|
|
||||||
with:
|
|
||||||
arch: "${{ steps.get-build-options.outputs.build-arch }}"
|
|
||||||
- name: "Import Secrets"
|
|
||||||
id: "import-secrets"
|
|
||||||
uses: "hashicorp/vault-action@v2"
|
|
||||||
with:
|
|
||||||
url: "https://vault.bthlabs.pl/"
|
|
||||||
method: "approle"
|
|
||||||
roleId: "${{ secrets.VAULT_ROLE_ID }}"
|
|
||||||
secretId: "${{ secrets.VAULT_SECRET_ID }}"
|
|
||||||
secrets: |
|
|
||||||
gitea/data/k8s.bthlab config | KUBECONFIG_PAYLOAD
|
|
||||||
- name: "Set up kubeconfig"
|
|
||||||
env:
|
|
||||||
COMPOSE_PROJECT: "${{ steps.get-run-info.outputs.compose-project }}"
|
|
||||||
KUBECONFIG_PAYLOAD: "${{ steps.import-secrets.outputs.KUBECONFIG_PAYLOAD }}"
|
|
||||||
run: |
|
|
||||||
set -x
|
|
||||||
|
|
||||||
echo ${KUBECONFIG_PAYLOAD} | base64 -d >"/opt/k8s/etc/kubeconfig"
|
|
||||||
export KUBECONFIG="/opt/k8s/etc/kubeconfig"
|
|
||||||
|
|
||||||
/opt/k8s/bin/kubectl config use-context ${KUBERNETES_CLUSTER}
|
|
||||||
/opt/k8s/bin/kubectl get node
|
|
||||||
- name: "Run `backend` Django migrations"
|
|
||||||
env:
|
|
||||||
COMPOSE_PROJECT: "${{ steps.get-run-info.outputs.compose-project }}"
|
|
||||||
BACKEND_TAG: "deployment-${{ steps.get-backend-version.outputs.version }}-${{ steps.get-backend-version.outputs.build-number }}"
|
|
||||||
run: |
|
|
||||||
set -x
|
|
||||||
|
|
||||||
(
|
|
||||||
cd deployment/hotpocket.bthlab ;
|
|
||||||
export KUBECONFIG="/opt/k8s/etc/kubeconfig" ;
|
|
||||||
/opt/k8s/bin/kubectl config use-context ${KUBERNETES_CLUSTER} ;
|
|
||||||
/opt/k8s/bin/kubectl -n ${KUBERNETES_NAMESPACE} set image cronjobs/backend-job-migrations migrations=docker-hosted.nexus.bthlabs.pl/hotpocket/backend:${BACKEND_TAG} ;
|
|
||||||
/opt/k8s/bin/kubectl -n ${KUBERNETES_NAMESPACE} delete jobs --ignore-not-found=true backend-job-migrations ;
|
|
||||||
/opt/k8s/bin/kubectl -n ${KUBERNETES_NAMESPACE} create job backend-job-migrations --from=cronjob/backend-job-migrations ;
|
|
||||||
/opt/k8s/bin/kubectl -n ${KUBERNETES_NAMESPACE} wait --for=condition=complete --timeout=300s job/backend-job-migrations
|
|
||||||
)
|
|
||||||
- name: "Deploy"
|
|
||||||
env:
|
|
||||||
COMPOSE_PROJECT: "${{ steps.get-run-info.outputs.compose-project }}"
|
|
||||||
BACKEND_TAG: "deployment-${{ steps.get-backend-version.outputs.version }}-${{ steps.get-backend-version.outputs.build-number }}"
|
|
||||||
run: |
|
|
||||||
set -x
|
|
||||||
(
|
|
||||||
cd deployment/hotpocket.bthlab ;
|
|
||||||
export KUBECONFIG="/opt/k8s/etc/kubeconfig" ;
|
|
||||||
/opt/k8s/bin/kubectl config use-context ${KUBERNETES_CLUSTER} ;
|
|
||||||
/opt/k8s/bin/kustomize edit set image hotpocket-backend=docker-hosted.nexus.bthlabs.pl/hotpocket/backend:${BACKEND_TAG} ;
|
|
||||||
/opt/k8s/bin/kustomize build . | /opt/k8s/bin/kubectl apply -f -
|
|
||||||
)
|
|
2
.gitignore
vendored
|
@ -1,4 +1,2 @@
|
||||||
.ci/
|
|
||||||
.envrc*
|
.envrc*
|
||||||
.ipythonhome/
|
.ipythonhome/
|
||||||
/docker-compose-ci-*.yaml
|
|
||||||
|
|
|
@ -86,9 +86,3 @@ Licensed under terms of the MIT License
|
||||||
Pepper Hot Solid icon
|
Pepper Hot Solid icon
|
||||||
Copyright (c) Icons8
|
Copyright (c) Icons8
|
||||||
Licensed under terms of the MIT License
|
Licensed under terms of the MIT License
|
||||||
|
|
||||||
Spinner Loader CSS from https://css-loaders.com/
|
|
||||||
|
|
||||||
cosmo, sandstone, sketchy and solar Bootswatch Themes
|
|
||||||
Copyright 2012-2025 Thomas Park
|
|
||||||
Licensed under terms of the MIT License
|
|
||||||
|
|
|
@ -66,7 +66,7 @@ $ docker run --rm -it \
|
||||||
-e HOTPOCKET_BACKEND_INITIAL_ACCOUNT_USERNAME=hotpocket \
|
-e HOTPOCKET_BACKEND_INITIAL_ACCOUNT_USERNAME=hotpocket \
|
||||||
-e HOTPOCKET_BACKEND_INITIAL_ACCOUNT_PASSWORD=hotpocketm4st3r \
|
-e HOTPOCKET_BACKEND_INITIAL_ACCOUNT_PASSWORD=hotpocketm4st3r \
|
||||||
-p 8000:8000 \
|
-p 8000:8000 \
|
||||||
docker-hosted.nexus.bthlabs.pl/hotpocket/backend:aio-v25.10.21-01
|
docker-hosted.nexus.bthlabs.pl/hotpocket/backend:aio-v25.9.12-01
|
||||||
```
|
```
|
||||||
|
|
||||||
The command above will set up and start the application. The SQLite file will
|
The command above will set up and start the application. The SQLite file will
|
||||||
|
@ -76,7 +76,8 @@ credentials. The Web app will be reachable at `http://127.0.0.1:8000/`.
|
||||||
The admin will be reachable at `http://127.0.0.1:8000/admin/`.
|
The admin will be reachable at `http://127.0.0.1:8000/admin/`.
|
||||||
|
|
||||||
The `DJANGO_SETTINGS_MODULE` environment variable defaults to
|
The `DJANGO_SETTINGS_MODULE` environment variable defaults to
|
||||||
`hotpocket_backend.settings.deployment.aio`.
|
`hotpocket_backend.settings.deployment.webapp`. This should be set to
|
||||||
|
`hotpocket_backend.settings.deployment.admin` in the Admin container.
|
||||||
|
|
||||||
**NOTE:** The command above specifies wildly insecure `SECRET_KEY` which is
|
**NOTE:** The command above specifies wildly insecure `SECRET_KEY` which is
|
||||||
used among other things to secure the session cookie. Please *please*
|
used among other things to secure the session cookie. Please *please*
|
||||||
|
@ -93,8 +94,7 @@ backend etc. The final deployment will require services for at least the Web
|
||||||
app, the Celery worker and Celery Beat. Admin is optional.
|
app, the Celery worker and Celery Beat. Admin is optional.
|
||||||
|
|
||||||
The `DJANGO_SETTINGS_MODULE` environment variable defaults to
|
The `DJANGO_SETTINGS_MODULE` environment variable defaults to
|
||||||
`hotpocket_backend.settings.deployment.webapp`. This should be set to
|
`hotpocket_backend.settings.deployment.aio`.
|
||||||
`hotpocket_backend.settings.deployment.admin` in the Admin container.
|
|
||||||
|
|
||||||
The `deployment/fullstack/docker-compose.yaml` file can be used as a
|
The `deployment/fullstack/docker-compose.yaml` file can be used as a
|
||||||
starting point for full-stack deployments.
|
starting point for full-stack deployments.
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
services:
|
services:
|
||||||
backend:
|
backend:
|
||||||
image: "docker-hosted.nexus.bthlabs.pl/hotpocket/backend:aio-v25.10.21-01"
|
image: "docker-hosted.nexus.bthlabs.pl/hotpocket/backend:aio-v25.9.12-01"
|
||||||
environment:
|
environment:
|
||||||
HOTPOCKET_BACKEND_SECRET_KEY: "thisisntright"
|
HOTPOCKET_BACKEND_SECRET_KEY: "thisisntright"
|
||||||
HOTPOCKET_BACKEND_INITIAL_ACCOUNT_USERNAME: "hotpocket"
|
HOTPOCKET_BACKEND_INITIAL_ACCOUNT_USERNAME: "hotpocket"
|
||||||
|
|
|
@ -8,7 +8,7 @@ x-backend-environment: &x-backend-environment
|
||||||
|
|
||||||
services:
|
services:
|
||||||
webapp:
|
webapp:
|
||||||
image: "docker-hosted.nexus.bthlabs.pl/hotpocket/backend:deployment-v25.10.21-01"
|
image: "docker-hosted.nexus.bthlabs.pl/hotpocket/backend:deployment-v25.9.12-01"
|
||||||
environment:
|
environment:
|
||||||
<<: *x-backend-environment
|
<<: *x-backend-environment
|
||||||
HOTPOCKET_BACKEND_ALLOWED_HOSTS: "app.staging.hotpocket.bthlab.bthlabs.net"
|
HOTPOCKET_BACKEND_ALLOWED_HOSTS: "app.staging.hotpocket.bthlab.bthlabs.net"
|
||||||
|
@ -21,7 +21,7 @@ services:
|
||||||
restart: "unless-stopped"
|
restart: "unless-stopped"
|
||||||
|
|
||||||
admin:
|
admin:
|
||||||
image: "docker-hosted.nexus.bthlabs.pl/hotpocket/backend:deployment-v25.10.21-01"
|
image: "docker-hosted.nexus.bthlabs.pl/hotpocket/backend:deployment-v25.9.12-01"
|
||||||
environment:
|
environment:
|
||||||
<<: *x-backend-environment
|
<<: *x-backend-environment
|
||||||
HOTPOCKET_BACKEND_APP: "admin"
|
HOTPOCKET_BACKEND_APP: "admin"
|
||||||
|
@ -35,7 +35,7 @@ services:
|
||||||
restart: "unless-stopped"
|
restart: "unless-stopped"
|
||||||
|
|
||||||
celery-worker:
|
celery-worker:
|
||||||
image: "docker-hosted.nexus.bthlabs.pl/hotpocket/backend:deployment-v25.10.21-01"
|
image: "docker-hosted.nexus.bthlabs.pl/hotpocket/backend:deployment-v25.9.12-01"
|
||||||
command:
|
command:
|
||||||
- "/srv/venv/bin/celery"
|
- "/srv/venv/bin/celery"
|
||||||
- "-A"
|
- "-A"
|
||||||
|
@ -57,7 +57,7 @@ services:
|
||||||
restart: "unless-stopped"
|
restart: "unless-stopped"
|
||||||
|
|
||||||
celery-beat:
|
celery-beat:
|
||||||
image: "docker-hosted.nexus.bthlabs.pl/hotpocket/backend:deployment-v25.10.21-01"
|
image: "docker-hosted.nexus.bthlabs.pl/hotpocket/backend:deployment-v25.9.12-01"
|
||||||
command:
|
command:
|
||||||
- "/srv/venv/bin/celery"
|
- "/srv/venv/bin/celery"
|
||||||
- "-A"
|
- "-A"
|
||||||
|
|
|
@ -1,5 +0,0 @@
|
||||||
DJANGO_SETTINGS_MODULE=hotpocket_backend.settings.deployment.admin
|
|
||||||
HOTPOCKET_BACKEND_GUNICORN_WORKERS=2
|
|
||||||
HOTPOCKET_BACKEND_APP=admin
|
|
||||||
HOTPOCKET_BACKEND_SECRET_KEY=thisissecret
|
|
||||||
HOTPOCKET_BACKEND_ALLOWED_HOSTS=thisissecret
|
|
|
@ -1,8 +0,0 @@
|
||||||
HOTPOCKET_BACKEND_ENV=deployment
|
|
||||||
HOTPOCKET_BACKEND_DATABASE_NAME=hotpocket_development_backend
|
|
||||||
HOTPOCKET_BACKEND_DATABASE_USER=thisissecret
|
|
||||||
HOTPOCKET_BACKEND_DATABASE_PASSWORD=thisissecret
|
|
||||||
HOTPOCKET_BACKEND_DATABASE_HOST=databases.bthlab
|
|
||||||
HOTPOCKET_BACKEND_CELERY_BROKER_URL=thisissecret
|
|
||||||
HOTPOCKET_BACKEND_CELERY_RESULT_BACKEND=thisissecret
|
|
||||||
HOTPOCKET_BACKEND_MODEL_AUTH_IS_DISABLED=false
|
|
|
@ -1,7 +0,0 @@
|
||||||
DJANGO_SETTINGS_MODULE=hotpocket_backend.settings.deployment.webapp
|
|
||||||
HOTPOCKET_BACKEND_GUNICORN_WORKERS=2
|
|
||||||
HOTPOCKET_BACKEND_APP=webapp
|
|
||||||
HOTPOCKET_BACKEND_SECRET_KEY=thisissecret
|
|
||||||
HOTPOCKET_BACKEND_ALLOWED_HOSTS=thisissecret
|
|
||||||
HOTPOCKET_BACKEND_SAVES_SAVE_ADAPTER=hotpocket_backend.apps.saves.adapters.postgres:PostgresSaveAdapter
|
|
||||||
HOTPOCKET_BACKEND_SAVES_ASSOCIATION_ADAPTER=hotpocket_backend.apps.saves.adapters.postgres:PostgresAssociationAdapter
|
|
|
@ -1,39 +0,0 @@
|
||||||
apiVersion: kustomize.config.k8s.io/v1beta1
|
|
||||||
kind: Kustomization
|
|
||||||
|
|
||||||
resources:
|
|
||||||
- resources/namespace.yaml
|
|
||||||
- resources/volumes.yaml
|
|
||||||
- resources/backend/job-migrations.yaml
|
|
||||||
- resources/backend/webapp.yaml
|
|
||||||
- resources/backend/webapp-service.yaml
|
|
||||||
- resources/backend/webapp-ingress.yaml
|
|
||||||
- resources/backend/admin.yaml
|
|
||||||
- resources/backend/admin-service.yaml
|
|
||||||
- resources/backend/admin-ingress.yaml
|
|
||||||
- resources/backend/celery-worker.yaml
|
|
||||||
- resources/backend/celery-beat.yaml
|
|
||||||
|
|
||||||
configMapGenerator:
|
|
||||||
- behavior: create
|
|
||||||
namespace: hotpocket-development
|
|
||||||
envs:
|
|
||||||
- configs/backend/base
|
|
||||||
name: backend-base-config
|
|
||||||
- behavior: create
|
|
||||||
namespace: hotpocket-development
|
|
||||||
envs:
|
|
||||||
- configs/backend/webapp
|
|
||||||
name: backend-webapp-config
|
|
||||||
- behavior: create
|
|
||||||
namespace: hotpocket-development
|
|
||||||
envs:
|
|
||||||
- configs/backend/admin
|
|
||||||
name: backend-admin-config
|
|
||||||
|
|
||||||
patches: []
|
|
||||||
|
|
||||||
images:
|
|
||||||
- name: hotpocket-backend
|
|
||||||
newName: docker-hosted.nexus.bthlabs.pl/hotpocket/backend
|
|
||||||
newTag: deployment-v25.10.4-01
|
|
|
@ -1,19 +0,0 @@
|
||||||
apiVersion: networking.k8s.io/v1
|
|
||||||
kind: Ingress
|
|
||||||
metadata:
|
|
||||||
name: backend-admin-ingress
|
|
||||||
namespace: hotpocket-development
|
|
||||||
annotations:
|
|
||||||
traefik.ingress.kubernetes.io/router.entrypoints: "web"
|
|
||||||
spec:
|
|
||||||
rules:
|
|
||||||
- host: admin.hotpocket.bthlab.bthlabs.net
|
|
||||||
http:
|
|
||||||
paths:
|
|
||||||
- path: /
|
|
||||||
pathType: Prefix
|
|
||||||
backend:
|
|
||||||
service:
|
|
||||||
name: backend-admin-service
|
|
||||||
port:
|
|
||||||
name: http
|
|
|
@ -1,14 +0,0 @@
|
||||||
apiVersion: v1
|
|
||||||
kind: Service
|
|
||||||
metadata:
|
|
||||||
name: backend-admin-service
|
|
||||||
namespace: hotpocket-development
|
|
||||||
spec:
|
|
||||||
type: ClusterIP
|
|
||||||
selector:
|
|
||||||
app.kubernetes.io/app: backend-admin
|
|
||||||
ports:
|
|
||||||
- name: http
|
|
||||||
protocol: TCP
|
|
||||||
port: 8000
|
|
||||||
targetPort: http
|
|
|
@ -1,101 +0,0 @@
|
||||||
apiVersion: apps/v1
|
|
||||||
kind: Deployment
|
|
||||||
metadata:
|
|
||||||
name: backend-admin
|
|
||||||
namespace: hotpocket-development
|
|
||||||
labels:
|
|
||||||
app.kubernetes.io/app: backend-admin
|
|
||||||
spec:
|
|
||||||
minReadySeconds: 30
|
|
||||||
progressDeadlineSeconds: 600
|
|
||||||
replicas: 1
|
|
||||||
revisionHistoryLimit: 1
|
|
||||||
strategy:
|
|
||||||
rollingUpdate:
|
|
||||||
maxSurge: 1
|
|
||||||
maxUnavailable: 1
|
|
||||||
type: RollingUpdate
|
|
||||||
selector:
|
|
||||||
matchLabels:
|
|
||||||
app.kubernetes.io/app: backend-admin
|
|
||||||
template:
|
|
||||||
metadata:
|
|
||||||
labels:
|
|
||||||
app.kubernetes.io/app: backend-admin
|
|
||||||
spec:
|
|
||||||
containers:
|
|
||||||
- name: app
|
|
||||||
image: hotpocket-backend:latest
|
|
||||||
command:
|
|
||||||
- "/srv/venv/bin/gunicorn"
|
|
||||||
- "-c"
|
|
||||||
- "/srv/lib/gunicorn.conf.py"
|
|
||||||
- "hotpocket_backend.wsgi:application"
|
|
||||||
envFrom:
|
|
||||||
- configMapRef:
|
|
||||||
name: backend-base-config
|
|
||||||
- configMapRef:
|
|
||||||
name: backend-admin-config
|
|
||||||
env:
|
|
||||||
- name: HOTPOCKET_BACKEND_SECRET_KEY
|
|
||||||
valueFrom:
|
|
||||||
secretKeyRef:
|
|
||||||
name: backend-admin
|
|
||||||
key: secret_key
|
|
||||||
- name: HOTPOCKET_BACKEND_ALLOWED_HOSTS
|
|
||||||
valueFrom:
|
|
||||||
secretKeyRef:
|
|
||||||
name: backend-admin
|
|
||||||
key: allowed_hosts
|
|
||||||
- name: HOTPOCKET_BACKEND_DATABASE_USER
|
|
||||||
valueFrom:
|
|
||||||
secretKeyRef:
|
|
||||||
name: backend-postgres
|
|
||||||
key: username
|
|
||||||
- name: HOTPOCKET_BACKEND_DATABASE_PASSWORD
|
|
||||||
valueFrom:
|
|
||||||
secretKeyRef:
|
|
||||||
name: backend-postgres
|
|
||||||
key: password
|
|
||||||
- name: HOTPOCKET_BACKEND_CELERY_BROKER_URL
|
|
||||||
valueFrom:
|
|
||||||
secretKeyRef:
|
|
||||||
name: backend-celery
|
|
||||||
key: broker_url
|
|
||||||
- name: HOTPOCKET_BACKEND_CELERY_RESULT_BACKEND
|
|
||||||
valueFrom:
|
|
||||||
secretKeyRef:
|
|
||||||
name: backend-celery
|
|
||||||
key: result_backend
|
|
||||||
ports:
|
|
||||||
- containerPort: 8000
|
|
||||||
name: http
|
|
||||||
protocol: TCP
|
|
||||||
- containerPort: 8001
|
|
||||||
name: healthcheck
|
|
||||||
protocol: TCP
|
|
||||||
livenessProbe:
|
|
||||||
httpGet:
|
|
||||||
path: "/"
|
|
||||||
port: 8001
|
|
||||||
initialDelaySeconds: 5
|
|
||||||
periodSeconds: 10
|
|
||||||
readinessProbe:
|
|
||||||
httpGet:
|
|
||||||
path: "/"
|
|
||||||
port: 8001
|
|
||||||
initialDelaySeconds: 2
|
|
||||||
periodSeconds: 5
|
|
||||||
volumeMounts:
|
|
||||||
- mountPath: /dev/shm
|
|
||||||
name: shm
|
|
||||||
- mountPath: /srv/run
|
|
||||||
name: backend-admin-srv-run
|
|
||||||
dnsPolicy: ClusterFirst
|
|
||||||
restartPolicy: Always
|
|
||||||
volumes:
|
|
||||||
- name: shm
|
|
||||||
emptyDir:
|
|
||||||
medium: Memory
|
|
||||||
- name: backend-admin-srv-run
|
|
||||||
emptyDir: {}
|
|
|
@ -1,85 +0,0 @@
|
||||||
apiVersion: apps/v1
|
|
||||||
kind: StatefulSet
|
|
||||||
metadata:
|
|
||||||
name: backend-celery-beat
|
|
||||||
namespace: hotpocket-development
|
|
||||||
labels:
|
|
||||||
app.kubernetes.io/app: backend-celery-beat
|
|
||||||
spec:
|
|
||||||
minReadySeconds: 30
|
|
||||||
replicas: 1
|
|
||||||
revisionHistoryLimit: 1
|
|
||||||
selector:
|
|
||||||
matchLabels:
|
|
||||||
app.kubernetes.io/app: backend-celery-beat
|
|
||||||
template:
|
|
||||||
metadata:
|
|
||||||
labels:
|
|
||||||
app.kubernetes.io/app: backend-celery-beat
|
|
||||||
spec:
|
|
||||||
containers:
|
|
||||||
- name: app
|
|
||||||
image: hotpocket-backend:latest
|
|
||||||
command:
|
|
||||||
- "/srv/venv/bin/celery"
|
|
||||||
- "-A"
|
|
||||||
- "hotpocket_backend.celery:app"
|
|
||||||
- "beat"
|
|
||||||
- "-l"
|
|
||||||
- "INFO"
|
|
||||||
- "-s"
|
|
||||||
- "/srv/run/celery-beat-schedule"
|
|
||||||
envFrom:
|
|
||||||
- configMapRef:
|
|
||||||
name: backend-base-config
|
|
||||||
- configMapRef:
|
|
||||||
name: backend-webapp-config
|
|
||||||
env:
|
|
||||||
- name: HOTPOCKET_BACKEND_SECRET_KEY
|
|
||||||
valueFrom:
|
|
||||||
secretKeyRef:
|
|
||||||
name: backend-webapp
|
|
||||||
key: secret_key
|
|
||||||
- name: HOTPOCKET_BACKEND_ALLOWED_HOSTS
|
|
||||||
valueFrom:
|
|
||||||
secretKeyRef:
|
|
||||||
name: backend-webapp
|
|
||||||
key: allowed_hosts
|
|
||||||
- name: HOTPOCKET_BACKEND_DATABASE_USER
|
|
||||||
valueFrom:
|
|
||||||
secretKeyRef:
|
|
||||||
name: backend-postgres
|
|
||||||
key: username
|
|
||||||
- name: HOTPOCKET_BACKEND_DATABASE_PASSWORD
|
|
||||||
valueFrom:
|
|
||||||
secretKeyRef:
|
|
||||||
name: backend-postgres
|
|
||||||
key: password
|
|
||||||
- name: HOTPOCKET_BACKEND_CELERY_BROKER_URL
|
|
||||||
valueFrom:
|
|
||||||
secretKeyRef:
|
|
||||||
name: backend-celery
|
|
||||||
key: broker_url
|
|
||||||
- name: HOTPOCKET_BACKEND_CELERY_RESULT_BACKEND
|
|
||||||
valueFrom:
|
|
||||||
secretKeyRef:
|
|
||||||
name: backend-celery
|
|
||||||
key: result_backend
|
|
||||||
volumeMounts:
|
|
||||||
- mountPath: /dev/shm
|
|
||||||
name: shm
|
|
||||||
- mountPath: /srv/run
|
|
||||||
name: backend-celery-beat-srv-run
|
|
||||||
- mountPath: /srv/uploads
|
|
||||||
name: backend-celery-beat-srv-uploads
|
|
||||||
dnsPolicy: ClusterFirst
|
|
||||||
restartPolicy: Always
|
|
||||||
volumes:
|
|
||||||
- name: shm
|
|
||||||
emptyDir:
|
|
||||||
medium: Memory
|
|
||||||
- name: backend-celery-beat-srv-run
|
|
||||||
persistentVolumeClaim:
|
|
||||||
claimName: backend-celery-beat-run
|
|
||||||
- name: backend-celery-beat-srv-uploads
|
|
||||||
emptyDir: {}
|
|
|
@ -1,93 +0,0 @@
|
||||||
apiVersion: apps/v1
|
|
||||||
kind: Deployment
|
|
||||||
metadata:
|
|
||||||
name: backend-celery-worker
|
|
||||||
namespace: hotpocket-development
|
|
||||||
labels:
|
|
||||||
app.kubernetes.io/app: backend-celery-worker
|
|
||||||
spec:
|
|
||||||
minReadySeconds: 30
|
|
||||||
progressDeadlineSeconds: 600
|
|
||||||
replicas: 1
|
|
||||||
revisionHistoryLimit: 1
|
|
||||||
strategy:
|
|
||||||
rollingUpdate:
|
|
||||||
maxSurge: 1
|
|
||||||
maxUnavailable: 1
|
|
||||||
type: RollingUpdate
|
|
||||||
selector:
|
|
||||||
matchLabels:
|
|
||||||
app.kubernetes.io/app: backend-celery-worker
|
|
||||||
template:
|
|
||||||
metadata:
|
|
||||||
labels:
|
|
||||||
app.kubernetes.io/app: backend-celery-worker
|
|
||||||
spec:
|
|
||||||
containers:
|
|
||||||
- name: app
|
|
||||||
image: hotpocket-backend:latest
|
|
||||||
command:
|
|
||||||
- "/srv/venv/bin/celery"
|
|
||||||
- "-A"
|
|
||||||
- "hotpocket_backend.celery:app"
|
|
||||||
- "worker"
|
|
||||||
- "-l"
|
|
||||||
- "INFO"
|
|
||||||
- "-Q"
|
|
||||||
- "celery,webapp"
|
|
||||||
- "-c"
|
|
||||||
- "2"
|
|
||||||
envFrom:
|
|
||||||
- configMapRef:
|
|
||||||
name: backend-base-config
|
|
||||||
- configMapRef:
|
|
||||||
name: backend-webapp-config
|
|
||||||
env:
|
|
||||||
- name: HOTPOCKET_BACKEND_SECRET_KEY
|
|
||||||
valueFrom:
|
|
||||||
secretKeyRef:
|
|
||||||
name: backend-webapp
|
|
||||||
key: secret_key
|
|
||||||
- name: HOTPOCKET_BACKEND_ALLOWED_HOSTS
|
|
||||||
valueFrom:
|
|
||||||
secretKeyRef:
|
|
||||||
name: backend-webapp
|
|
||||||
key: allowed_hosts
|
|
||||||
- name: HOTPOCKET_BACKEND_DATABASE_USER
|
|
||||||
valueFrom:
|
|
||||||
secretKeyRef:
|
|
||||||
name: backend-postgres
|
|
||||||
key: username
|
|
||||||
- name: HOTPOCKET_BACKEND_DATABASE_PASSWORD
|
|
||||||
valueFrom:
|
|
||||||
secretKeyRef:
|
|
||||||
name: backend-postgres
|
|
||||||
key: password
|
|
||||||
- name: HOTPOCKET_BACKEND_CELERY_BROKER_URL
|
|
||||||
valueFrom:
|
|
||||||
secretKeyRef:
|
|
||||||
name: backend-celery
|
|
||||||
key: broker_url
|
|
||||||
- name: HOTPOCKET_BACKEND_CELERY_RESULT_BACKEND
|
|
||||||
valueFrom:
|
|
||||||
secretKeyRef:
|
|
||||||
name: backend-celery
|
|
||||||
key: result_backend
|
|
||||||
volumeMounts:
|
|
||||||
- mountPath: /dev/shm
|
|
||||||
name: shm
|
|
||||||
- mountPath: /srv/run
|
|
||||||
name: backend-celery-worker-srv-run
|
|
||||||
- mountPath: /srv/uploads
|
|
||||||
name: backend-celery-worker-srv-uploads
|
|
||||||
dnsPolicy: ClusterFirst
|
|
||||||
restartPolicy: Always
|
|
||||||
volumes:
|
|
||||||
- name: shm
|
|
||||||
emptyDir:
|
|
||||||
medium: Memory
|
|
||||||
- name: backend-celery-worker-srv-run
|
|
||||||
emptyDir: {}
|
|
||||||
- name: backend-celery-worker-srv-uploads
|
|
||||||
persistentVolumeClaim:
|
|
||||||
claimName: backend-uploads
|
|
|
@ -1,80 +0,0 @@
|
||||||
apiVersion: batch/v1
|
|
||||||
kind: CronJob
|
|
||||||
metadata:
|
|
||||||
name: backend-job-migrations
|
|
||||||
namespace: hotpocket-development
|
|
||||||
labels:
|
|
||||||
app.kubernetes.io/app: backend-job-migrations
|
|
||||||
spec:
|
|
||||||
concurrencyPolicy: "Forbid"
|
|
||||||
successfulJobsHistoryLimit: 1
|
|
||||||
failedJobsHistoryLimit: 1
|
|
||||||
startingDeadlineSeconds: 180
|
|
||||||
schedule: "* * * * *"
|
|
||||||
suspend: true
|
|
||||||
jobTemplate:
|
|
||||||
spec:
|
|
||||||
backoffLimit: 1
|
|
||||||
completions: 1
|
|
||||||
parallelism: 1
|
|
||||||
template:
|
|
||||||
spec:
|
|
||||||
containers:
|
|
||||||
- name: migrations
|
|
||||||
image: hotpocket-backend:latest
|
|
||||||
command:
|
|
||||||
- "./manage.py"
|
|
||||||
- "migrate"
|
|
||||||
envFrom:
|
|
||||||
- configMapRef:
|
|
||||||
name: backend-base-config
|
|
||||||
- configMapRef:
|
|
||||||
name: backend-webapp-config
|
|
||||||
env:
|
|
||||||
- name: HOTPOCKET_BACKEND_SECRET_KEY
|
|
||||||
valueFrom:
|
|
||||||
secretKeyRef:
|
|
||||||
name: backend-webapp
|
|
||||||
key: secret_key
|
|
||||||
- name: HOTPOCKET_BACKEND_ALLOWED_HOSTS
|
|
||||||
valueFrom:
|
|
||||||
secretKeyRef:
|
|
||||||
name: backend-webapp
|
|
||||||
key: allowed_hosts
|
|
||||||
- name: HOTPOCKET_BACKEND_DATABASE_USER
|
|
||||||
valueFrom:
|
|
||||||
secretKeyRef:
|
|
||||||
name: backend-postgres
|
|
||||||
key: username
|
|
||||||
- name: HOTPOCKET_BACKEND_DATABASE_PASSWORD
|
|
||||||
valueFrom:
|
|
||||||
secretKeyRef:
|
|
||||||
name: backend-postgres
|
|
||||||
key: password
|
|
||||||
- name: HOTPOCKET_BACKEND_CELERY_BROKER_URL
|
|
||||||
valueFrom:
|
|
||||||
secretKeyRef:
|
|
||||||
name: backend-celery
|
|
||||||
key: broker_url
|
|
||||||
- name: HOTPOCKET_BACKEND_CELERY_RESULT_BACKEND
|
|
||||||
valueFrom:
|
|
||||||
secretKeyRef:
|
|
||||||
name: backend-celery
|
|
||||||
key: result_backend
|
|
||||||
volumeMounts:
|
|
||||||
- mountPath: /dev/shm
|
|
||||||
name: shm
|
|
||||||
- mountPath: /srv/run
|
|
||||||
name: backend-webapp-srv-run
|
|
||||||
- mountPath: /srv/uploads
|
|
||||||
name: backend-webapp-srv-uploads
|
|
||||||
dnsPolicy: ClusterFirst
|
|
||||||
restartPolicy: Never
|
|
||||||
volumes:
|
|
||||||
- name: shm
|
|
||||||
emptyDir:
|
|
||||||
medium: Memory
|
|
||||||
- name: backend-webapp-srv-run
|
|
||||||
emptyDir: {}
|
|
||||||
- name: backend-webapp-srv-uploads
|
|
||||||
emptyDir: {}
|
|
|
@ -1,19 +0,0 @@
|
||||||
apiVersion: networking.k8s.io/v1
|
|
||||||
kind: Ingress
|
|
||||||
metadata:
|
|
||||||
name: backend-webapp-ingress
|
|
||||||
namespace: hotpocket-development
|
|
||||||
annotations:
|
|
||||||
traefik.ingress.kubernetes.io/router.entrypoints: "web"
|
|
||||||
spec:
|
|
||||||
rules:
|
|
||||||
- host: app.hotpocket.bthlab.bthlabs.net
|
|
||||||
http:
|
|
||||||
paths:
|
|
||||||
- path: /
|
|
||||||
pathType: Prefix
|
|
||||||
backend:
|
|
||||||
service:
|
|
||||||
name: backend-webapp-service
|
|
||||||
port:
|
|
||||||
name: http
|
|
|
@ -1,14 +0,0 @@
|
||||||
apiVersion: v1
|
|
||||||
kind: Service
|
|
||||||
metadata:
|
|
||||||
name: backend-webapp-service
|
|
||||||
namespace: hotpocket-development
|
|
||||||
spec:
|
|
||||||
type: ClusterIP
|
|
||||||
selector:
|
|
||||||
app.kubernetes.io/app: backend-webapp
|
|
||||||
ports:
|
|
||||||
- name: http
|
|
||||||
protocol: TCP
|
|
||||||
port: 8000
|
|
||||||
targetPort: http
|
|
|
@ -1,106 +0,0 @@
|
||||||
apiVersion: apps/v1
|
|
||||||
kind: Deployment
|
|
||||||
metadata:
|
|
||||||
name: backend-webapp
|
|
||||||
namespace: hotpocket-development
|
|
||||||
labels:
|
|
||||||
app.kubernetes.io/app: backend-webapp
|
|
||||||
spec:
|
|
||||||
minReadySeconds: 30
|
|
||||||
progressDeadlineSeconds: 600
|
|
||||||
replicas: 1
|
|
||||||
revisionHistoryLimit: 1
|
|
||||||
strategy:
|
|
||||||
rollingUpdate:
|
|
||||||
maxSurge: 1
|
|
||||||
maxUnavailable: 1
|
|
||||||
type: RollingUpdate
|
|
||||||
selector:
|
|
||||||
matchLabels:
|
|
||||||
app.kubernetes.io/app: backend-webapp
|
|
||||||
template:
|
|
||||||
metadata:
|
|
||||||
labels:
|
|
||||||
app.kubernetes.io/app: backend-webapp
|
|
||||||
spec:
|
|
||||||
containers:
|
|
||||||
- name: app
|
|
||||||
image: hotpocket-backend:latest
|
|
||||||
command:
|
|
||||||
- "/srv/venv/bin/gunicorn"
|
|
||||||
- "-c"
|
|
||||||
- "/srv/lib/gunicorn.conf.py"
|
|
||||||
- "hotpocket_backend.wsgi:application"
|
|
||||||
envFrom:
|
|
||||||
- configMapRef:
|
|
||||||
name: backend-base-config
|
|
||||||
- configMapRef:
|
|
||||||
name: backend-webapp-config
|
|
||||||
env:
|
|
||||||
- name: HOTPOCKET_BACKEND_SECRET_KEY
|
|
||||||
valueFrom:
|
|
||||||
secretKeyRef:
|
|
||||||
name: backend-webapp
|
|
||||||
key: secret_key
|
|
||||||
- name: HOTPOCKET_BACKEND_ALLOWED_HOSTS
|
|
||||||
valueFrom:
|
|
||||||
secretKeyRef:
|
|
||||||
name: backend-webapp
|
|
||||||
key: allowed_hosts
|
|
||||||
- name: HOTPOCKET_BACKEND_DATABASE_USER
|
|
||||||
valueFrom:
|
|
||||||
secretKeyRef:
|
|
||||||
name: backend-postgres
|
|
||||||
key: username
|
|
||||||
- name: HOTPOCKET_BACKEND_DATABASE_PASSWORD
|
|
||||||
valueFrom:
|
|
||||||
secretKeyRef:
|
|
||||||
name: backend-postgres
|
|
||||||
key: password
|
|
||||||
- name: HOTPOCKET_BACKEND_CELERY_BROKER_URL
|
|
||||||
valueFrom:
|
|
||||||
secretKeyRef:
|
|
||||||
name: backend-celery
|
|
||||||
key: broker_url
|
|
||||||
- name: HOTPOCKET_BACKEND_CELERY_RESULT_BACKEND
|
|
||||||
valueFrom:
|
|
||||||
secretKeyRef:
|
|
||||||
name: backend-celery
|
|
||||||
key: result_backend
|
|
||||||
ports:
|
|
||||||
- containerPort: 8000
|
|
||||||
name: http
|
|
||||||
protocol: TCP
|
|
||||||
- containerPort: 8001
|
|
||||||
name: healthcheck
|
|
||||||
protocol: TCP
|
|
||||||
livenessProbe:
|
|
||||||
httpGet:
|
|
||||||
path: "/"
|
|
||||||
port: 8001
|
|
||||||
initialDelaySeconds: 5
|
|
||||||
periodSeconds: 10
|
|
||||||
readinessProbe:
|
|
||||||
httpGet:
|
|
||||||
path: "/"
|
|
||||||
port: 8001
|
|
||||||
initialDelaySeconds: 2
|
|
||||||
periodSeconds: 5
|
|
||||||
volumeMounts:
|
|
||||||
- mountPath: /dev/shm
|
|
||||||
name: shm
|
|
||||||
- mountPath: /srv/run
|
|
||||||
name: backend-webapp-srv-run
|
|
||||||
- mountPath: /srv/uploads
|
|
||||||
name: backend-webapp-srv-uploads
|
|
||||||
dnsPolicy: ClusterFirst
|
|
||||||
restartPolicy: Always
|
|
||||||
volumes:
|
|
||||||
- name: shm
|
|
||||||
emptyDir:
|
|
||||||
medium: Memory
|
|
||||||
- name: backend-webapp-srv-run
|
|
||||||
emptyDir: {}
|
|
||||||
- name: backend-webapp-srv-uploads
|
|
||||||
persistentVolumeClaim:
|
|
||||||
claimName: backend-uploads
|
|
|
@ -1,4 +0,0 @@
|
||||||
apiVersion: v1
|
|
||||||
kind: Namespace
|
|
||||||
metadata:
|
|
||||||
name: hotpocket-development
|
|
|
@ -1,26 +0,0 @@
|
||||||
---
|
|
||||||
apiVersion: v1
|
|
||||||
kind: PersistentVolumeClaim
|
|
||||||
metadata:
|
|
||||||
name: backend-uploads
|
|
||||||
namespace: hotpocket-development
|
|
||||||
spec:
|
|
||||||
storageClassName: nfs-client
|
|
||||||
accessModes:
|
|
||||||
- ReadWriteMany
|
|
||||||
resources:
|
|
||||||
requests:
|
|
||||||
storage: "1Gi"
|
|
||||||
---
|
|
||||||
apiVersion: v1
|
|
||||||
kind: PersistentVolumeClaim
|
|
||||||
metadata:
|
|
||||||
name: backend-celery-beat-run
|
|
||||||
namespace: hotpocket-development
|
|
||||||
spec:
|
|
||||||
storageClassName: nfs-client
|
|
||||||
accessModes:
|
|
||||||
- ReadWriteMany
|
|
||||||
resources:
|
|
||||||
requests:
|
|
||||||
storage: "1Gi"
|
|
|
@ -2,7 +2,6 @@
|
||||||
"group": {
|
"group": {
|
||||||
"default": {
|
"default": {
|
||||||
"targets": [
|
"targets": [
|
||||||
"apple-management",
|
|
||||||
"backend-management",
|
"backend-management",
|
||||||
"caddy",
|
"caddy",
|
||||||
"extension-management",
|
"extension-management",
|
||||||
|
@ -14,28 +13,6 @@
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"target": {
|
"target": {
|
||||||
"apple-management": {
|
|
||||||
"context": "services/",
|
|
||||||
"dockerfile": "apple/Dockerfile",
|
|
||||||
"tags": [
|
|
||||||
"docker-hosted.nexus.bthlabs.pl/hotpocket/apple:local"
|
|
||||||
],
|
|
||||||
"target": "development",
|
|
||||||
"output": [
|
|
||||||
"type=docker,load=true,push=false"
|
|
||||||
]
|
|
||||||
},
|
|
||||||
"apple-ci": {
|
|
||||||
"context": "services/",
|
|
||||||
"dockerfile": "apple/Dockerfile",
|
|
||||||
"tags": [
|
|
||||||
"docker-hosted.nexus.bthlabs.pl/hotpocket/apple:ci-local"
|
|
||||||
],
|
|
||||||
"target": "ci",
|
|
||||||
"output": [
|
|
||||||
"type=docker,load=true,push=false"
|
|
||||||
]
|
|
||||||
},
|
|
||||||
"backend-management": {
|
"backend-management": {
|
||||||
"context": "services/",
|
"context": "services/",
|
||||||
"dockerfile": "backend/Dockerfile",
|
"dockerfile": "backend/Dockerfile",
|
||||||
|
|
|
@ -1,17 +1,16 @@
|
||||||
services:
|
services:
|
||||||
postgres:
|
postgres:
|
||||||
ports: !override []
|
ports: []
|
||||||
|
|
||||||
keycloak:
|
keycloak:
|
||||||
command: "echo 'NOOP'"
|
command: "echo 'NOOP'"
|
||||||
ports: !override []
|
ports: []
|
||||||
restart: "no"
|
restart: "no"
|
||||||
|
|
||||||
rabbitmq:
|
rabbitmq:
|
||||||
ports: !override []
|
ports: []
|
||||||
|
|
||||||
include:
|
include:
|
||||||
- path: "./services/backend/docker-compose-ci.yaml"
|
- path: "./services/backend/docker-compose-ci.yaml"
|
||||||
- path: "./services/packages/docker-compose-ci.yaml"
|
- path: "./services/packages/docker-compose-ci.yaml"
|
||||||
- path: "./services/extension/docker-compose-ci.yaml"
|
- path: "./services/extension/docker-compose-ci.yaml"
|
||||||
- path: "./services/apple/docker-compose-ci.yaml"
|
|
||||||
|
|
|
@ -6,7 +6,6 @@ include:
|
||||||
- path: "./services/backend/docker-compose.yaml"
|
- path: "./services/backend/docker-compose.yaml"
|
||||||
- path: "./services/packages/docker-compose.yaml"
|
- path: "./services/packages/docker-compose.yaml"
|
||||||
- path: "./services/extension/docker-compose.yaml"
|
- path: "./services/extension/docker-compose.yaml"
|
||||||
- path: "./services/apple/docker-compose.yaml"
|
|
||||||
|
|
||||||
volumes: {}
|
volumes: {}
|
||||||
|
|
||||||
|
|
|
@ -4,5 +4,4 @@ run:
|
||||||
files_to_version:
|
files_to_version:
|
||||||
- "deployment/aio/docker-compose.yaml"
|
- "deployment/aio/docker-compose.yaml"
|
||||||
- "deployment/fullstack/docker-compose.yaml"
|
- "deployment/fullstack/docker-compose.yaml"
|
||||||
- "pyproject.toml"
|
|
||||||
- "README.md"
|
- "README.md"
|
||||||
|
|
17
poetry.lock
generated
|
@ -1,4 +1,4 @@
|
||||||
# This file is automatically @generated by Poetry 2.2.1 and should not be changed by hand.
|
# This file is automatically @generated by Poetry 1.8.3 and should not be changed by hand.
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "hotpocket-workspace-tools"
|
name = "hotpocket-workspace-tools"
|
||||||
|
@ -6,30 +6,25 @@ version = "1.0.0.dev0"
|
||||||
description = "HotPocket Workspace Tools"
|
description = "HotPocket Workspace Tools"
|
||||||
optional = false
|
optional = false
|
||||||
python-versions = "^3.12"
|
python-versions = "^3.12"
|
||||||
groups = ["main"]
|
|
||||||
files = []
|
files = []
|
||||||
develop = true
|
develop = true
|
||||||
|
|
||||||
[package.dependencies]
|
|
||||||
invoke = "2.2.1"
|
|
||||||
|
|
||||||
[package.source]
|
[package.source]
|
||||||
type = "directory"
|
type = "directory"
|
||||||
url = "services/packages/workspace_tools"
|
url = "services/packages/workspace_tools"
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "invoke"
|
name = "invoke"
|
||||||
version = "2.2.1"
|
version = "2.2.0"
|
||||||
description = "Pythonic task execution"
|
description = "Pythonic task execution"
|
||||||
optional = false
|
optional = false
|
||||||
python-versions = ">=3.6"
|
python-versions = ">=3.6"
|
||||||
groups = ["main"]
|
|
||||||
files = [
|
files = [
|
||||||
{file = "invoke-2.2.1-py3-none-any.whl", hash = "sha256:2413bc441b376e5cd3f55bb5d364f973ad8bdd7bf87e53c79de3c11bf3feecc8"},
|
{file = "invoke-2.2.0-py3-none-any.whl", hash = "sha256:6ea924cc53d4f78e3d98bc436b08069a03077e6f85ad1ddaa8a116d7dad15820"},
|
||||||
{file = "invoke-2.2.1.tar.gz", hash = "sha256:515bf49b4a48932b79b024590348da22f39c4942dff991ad1fb8b8baea1be707"},
|
{file = "invoke-2.2.0.tar.gz", hash = "sha256:ee6cbb101af1a859c7fe84f2a264c059020b0cb7fe3535f9424300ab568f6bd5"},
|
||||||
]
|
]
|
||||||
|
|
||||||
[metadata]
|
[metadata]
|
||||||
lock-version = "2.1"
|
lock-version = "2.0"
|
||||||
python-versions = "^3.12"
|
python-versions = "^3.12"
|
||||||
content-hash = "a7028d4a0260c82012077d9cc4b324b0ef5ab8ed24aa283a51cf941ba09685a9"
|
content-hash = "ec33c3b3ec0f988e333872bdd134c1adce0782e98512dd2484cb85009b3da6cb"
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
[tool.poetry]
|
[tool.poetry]
|
||||||
name = "hotpocket-workspace"
|
name = "hotpocket-workspace"
|
||||||
version = "25.10.21"
|
version = "1.0.0"
|
||||||
description = "HotPocket Workspace"
|
description = "HotPocket Workspace"
|
||||||
authors = ["Tomek Wójcik <contact@bthlabs.pl>"]
|
authors = ["Tomek Wójcik <contact@bthlabs.pl>"]
|
||||||
license = "Apache-2.0"
|
license = "Apache-2.0"
|
||||||
|
@ -9,6 +9,7 @@ package-mode = false
|
||||||
[tool.poetry.dependencies]
|
[tool.poetry.dependencies]
|
||||||
python = "^3.12"
|
python = "^3.12"
|
||||||
hotpocket-workspace-tools = {path = "services/packages/workspace_tools", develop = true}
|
hotpocket-workspace-tools = {path = "services/packages/workspace_tools", develop = true}
|
||||||
|
invoke = "2.2.0"
|
||||||
|
|
||||||
[build-system]
|
[build-system]
|
||||||
requires = ["poetry-core"]
|
requires = ["poetry-core"]
|
||||||
|
|
|
@ -1,8 +1,5 @@
|
||||||
.mypy_cache/
|
|
||||||
.pytest_cache/
|
|
||||||
_tmp/
|
_tmp/
|
||||||
apple/build/
|
apple/
|
||||||
apple/DerivedData/
|
|
||||||
backend/node_modules/
|
backend/node_modules/
|
||||||
backend/ops/metal/
|
backend/ops/metal/
|
||||||
backend/hotpocket_backend/playground.py
|
backend/hotpocket_backend/playground.py
|
||||||
|
|
|
@ -1,19 +0,0 @@
|
||||||
ARG APP_USER_UID=1000
|
|
||||||
ARG APP_USER_GID=1000
|
|
||||||
ARG IMAGE_ID=development.00000000
|
|
||||||
|
|
||||||
FROM docker-hosted.nexus.bthlabs.pl/hotpocket/base:build-node-20251014-01 AS development
|
|
||||||
|
|
||||||
ARG APP_USER_UID
|
|
||||||
ARG APP_USER_GID
|
|
||||||
ARG IMAGE_ID
|
|
||||||
|
|
||||||
# COPY --chown=$APP_USER_UID:$APP_USER_GID apple/ops/bin/*.sh /srv/bin/
|
|
||||||
|
|
||||||
VOLUME ["/srv/node_modules", "/srv/venv"]
|
|
||||||
|
|
||||||
FROM development AS ci
|
|
||||||
|
|
||||||
COPY --chown=$APP_USER_UID:$APP_USER_GID apple/ /srv/app/
|
|
||||||
COPY --chown=$APP_USER_UID:$APP_USER_GID packages/ /srv/packages/
|
|
||||||
COPY --chown=$APP_USER_UID:$APP_USER_GID tls/ /srv/tls/
|
|
|
@ -7,33 +7,11 @@
|
||||||
objects = {
|
objects = {
|
||||||
|
|
||||||
/* Begin PBXBuildFile section */
|
/* Begin PBXBuildFile section */
|
||||||
4C1159202E8B055F003B34AD /* Save to HotPocket.appex in Embed Foundation Extensions */ = {isa = PBXBuildFile; fileRef = 4CBCEA4F2E81CB9500722009 /* Save to HotPocket.appex */; settings = {ATTRIBUTES = (RemoveHeadersOnCopy, ); }; };
|
|
||||||
4C2F0C692E851BBD0033F5C2 /* Save to HotPocket.appex in Embed Foundation Extensions */ = {isa = PBXBuildFile; fileRef = 4C2F0C5E2E851BBD0033F5C2 /* Save to HotPocket.appex */; settings = {ATTRIBUTES = (RemoveHeadersOnCopy, ); }; };
|
|
||||||
4C70F30D2E8869FB00320048 /* HPShareExtensionHelper.m in Sources */ = {isa = PBXBuildFile; fileRef = 4C70F30C2E8869FB00320048 /* HPShareExtensionHelper.m */; };
|
|
||||||
4C70F30E2E8869FB00320048 /* HPShareExtensionHelper.m in Sources */ = {isa = PBXBuildFile; fileRef = 4C70F30C2E8869FB00320048 /* HPShareExtensionHelper.m */; };
|
|
||||||
4C70F3152E886A8F00320048 /* HPSharedItem.m in Sources */ = {isa = PBXBuildFile; fileRef = 4C70F3142E886A8F00320048 /* HPSharedItem.m */; };
|
|
||||||
4C70F3162E886A8F00320048 /* HPSharedItem.m in Sources */ = {isa = PBXBuildFile; fileRef = 4C70F3142E886A8F00320048 /* HPSharedItem.m */; };
|
|
||||||
4C70F3192E886ADD00320048 /* HPSharedItemsContainer.m in Sources */ = {isa = PBXBuildFile; fileRef = 4C70F3182E886ADD00320048 /* HPSharedItemsContainer.m */; };
|
|
||||||
4C70F31A2E886ADD00320048 /* HPSharedItemsContainer.m in Sources */ = {isa = PBXBuildFile; fileRef = 4C70F3182E886ADD00320048 /* HPSharedItemsContainer.m */; };
|
|
||||||
4CABCAD62E56F0C900D8A354 /* HotPocket Extension.appex in Embed Foundation Extensions */ = {isa = PBXBuildFile; fileRef = 4CABCAD52E56F0C900D8A354 /* HotPocket Extension.appex */; settings = {ATTRIBUTES = (RemoveHeadersOnCopy, ); }; };
|
4CABCAD62E56F0C900D8A354 /* HotPocket Extension.appex in Embed Foundation Extensions */ = {isa = PBXBuildFile; fileRef = 4CABCAD52E56F0C900D8A354 /* HotPocket Extension.appex */; settings = {ATTRIBUTES = (RemoveHeadersOnCopy, ); }; };
|
||||||
4CABCAE02E56F0C900D8A354 /* HotPocket Extension.appex in Embed Foundation Extensions */ = {isa = PBXBuildFile; fileRef = 4CABCADF2E56F0C900D8A354 /* HotPocket Extension.appex */; settings = {ATTRIBUTES = (RemoveHeadersOnCopy, ); }; };
|
4CABCAE02E56F0C900D8A354 /* HotPocket Extension.appex in Embed Foundation Extensions */ = {isa = PBXBuildFile; fileRef = 4CABCADF2E56F0C900D8A354 /* HotPocket Extension.appex */; settings = {ATTRIBUTES = (RemoveHeadersOnCopy, ); }; };
|
||||||
/* End PBXBuildFile section */
|
/* End PBXBuildFile section */
|
||||||
|
|
||||||
/* Begin PBXContainerItemProxy section */
|
/* Begin PBXContainerItemProxy section */
|
||||||
4C1159212E8B055F003B34AD /* PBXContainerItemProxy */ = {
|
|
||||||
isa = PBXContainerItemProxy;
|
|
||||||
containerPortal = 4CABCA922E56F0C800D8A354 /* Project object */;
|
|
||||||
proxyType = 1;
|
|
||||||
remoteGlobalIDString = 4CBCEA4E2E81CB9500722009;
|
|
||||||
remoteInfo = "macOS (Share Extension)";
|
|
||||||
};
|
|
||||||
4C2F0C672E851BBD0033F5C2 /* PBXContainerItemProxy */ = {
|
|
||||||
isa = PBXContainerItemProxy;
|
|
||||||
containerPortal = 4CABCA922E56F0C800D8A354 /* Project object */;
|
|
||||||
proxyType = 1;
|
|
||||||
remoteGlobalIDString = 4C2F0C5D2E851BBD0033F5C2;
|
|
||||||
remoteInfo = "iOS (Share Extension)";
|
|
||||||
};
|
|
||||||
4CABCAD72E56F0C900D8A354 /* PBXContainerItemProxy */ = {
|
4CABCAD72E56F0C900D8A354 /* PBXContainerItemProxy */ = {
|
||||||
isa = PBXContainerItemProxy;
|
isa = PBXContainerItemProxy;
|
||||||
containerPortal = 4CABCA922E56F0C800D8A354 /* Project object */;
|
containerPortal = 4CABCA922E56F0C800D8A354 /* Project object */;
|
||||||
|
@ -58,7 +36,6 @@
|
||||||
dstSubfolderSpec = 13;
|
dstSubfolderSpec = 13;
|
||||||
files = (
|
files = (
|
||||||
4CABCAD62E56F0C900D8A354 /* HotPocket Extension.appex in Embed Foundation Extensions */,
|
4CABCAD62E56F0C900D8A354 /* HotPocket Extension.appex in Embed Foundation Extensions */,
|
||||||
4C2F0C692E851BBD0033F5C2 /* Save to HotPocket.appex in Embed Foundation Extensions */,
|
|
||||||
);
|
);
|
||||||
name = "Embed Foundation Extensions";
|
name = "Embed Foundation Extensions";
|
||||||
runOnlyForDeploymentPostprocessing = 0;
|
runOnlyForDeploymentPostprocessing = 0;
|
||||||
|
@ -69,7 +46,6 @@
|
||||||
dstPath = "";
|
dstPath = "";
|
||||||
dstSubfolderSpec = 13;
|
dstSubfolderSpec = 13;
|
||||||
files = (
|
files = (
|
||||||
4C1159202E8B055F003B34AD /* Save to HotPocket.appex in Embed Foundation Extensions */,
|
|
||||||
4CABCAE02E56F0C900D8A354 /* HotPocket Extension.appex in Embed Foundation Extensions */,
|
4CABCAE02E56F0C900D8A354 /* HotPocket Extension.appex in Embed Foundation Extensions */,
|
||||||
);
|
);
|
||||||
name = "Embed Foundation Extensions";
|
name = "Embed Foundation Extensions";
|
||||||
|
@ -78,64 +54,22 @@
|
||||||
/* End PBXCopyFilesBuildPhase section */
|
/* End PBXCopyFilesBuildPhase section */
|
||||||
|
|
||||||
/* Begin PBXFileReference section */
|
/* Begin PBXFileReference section */
|
||||||
4C2F0C5E2E851BBD0033F5C2 /* Save to HotPocket.appex */ = {isa = PBXFileReference; explicitFileType = "wrapper.app-extension"; includeInIndex = 0; path = "Save to HotPocket.appex"; sourceTree = BUILT_PRODUCTS_DIR; };
|
|
||||||
4C70F30B2E8869FB00320048 /* HPShareExtensionHelper.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = HPShareExtensionHelper.h; sourceTree = "<group>"; };
|
|
||||||
4C70F30C2E8869FB00320048 /* HPShareExtensionHelper.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = HPShareExtensionHelper.m; sourceTree = "<group>"; };
|
|
||||||
4C70F3132E886A8F00320048 /* HPSharedItem.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = HPSharedItem.h; sourceTree = "<group>"; };
|
|
||||||
4C70F3142E886A8F00320048 /* HPSharedItem.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = HPSharedItem.m; sourceTree = "<group>"; };
|
|
||||||
4C70F3172E886ADD00320048 /* HPSharedItemsContainer.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = HPSharedItemsContainer.h; sourceTree = "<group>"; };
|
|
||||||
4C70F3182E886ADD00320048 /* HPSharedItemsContainer.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = HPSharedItemsContainer.m; sourceTree = "<group>"; };
|
|
||||||
4CABCAB02E56F0C900D8A354 /* HotPocket.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = HotPocket.app; sourceTree = BUILT_PRODUCTS_DIR; };
|
4CABCAB02E56F0C900D8A354 /* HotPocket.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = HotPocket.app; sourceTree = BUILT_PRODUCTS_DIR; };
|
||||||
4CABCAC62E56F0C900D8A354 /* HotPocket.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = HotPocket.app; sourceTree = BUILT_PRODUCTS_DIR; };
|
4CABCAC62E56F0C900D8A354 /* HotPocket.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = HotPocket.app; sourceTree = BUILT_PRODUCTS_DIR; };
|
||||||
4CABCAD52E56F0C900D8A354 /* HotPocket Extension.appex */ = {isa = PBXFileReference; explicitFileType = "wrapper.app-extension"; includeInIndex = 0; path = "HotPocket Extension.appex"; sourceTree = BUILT_PRODUCTS_DIR; };
|
4CABCAD52E56F0C900D8A354 /* HotPocket Extension.appex */ = {isa = PBXFileReference; explicitFileType = "wrapper.app-extension"; includeInIndex = 0; path = "HotPocket Extension.appex"; sourceTree = BUILT_PRODUCTS_DIR; };
|
||||||
4CABCADF2E56F0C900D8A354 /* HotPocket Extension.appex */ = {isa = PBXFileReference; explicitFileType = "wrapper.app-extension"; includeInIndex = 0; path = "HotPocket Extension.appex"; sourceTree = BUILT_PRODUCTS_DIR; };
|
4CABCADF2E56F0C900D8A354 /* HotPocket Extension.appex */ = {isa = PBXFileReference; explicitFileType = "wrapper.app-extension"; includeInIndex = 0; path = "HotPocket Extension.appex"; sourceTree = BUILT_PRODUCTS_DIR; };
|
||||||
4CBCEA4F2E81CB9500722009 /* Save to HotPocket.appex */ = {isa = PBXFileReference; explicitFileType = "wrapper.app-extension"; includeInIndex = 0; path = "Save to HotPocket.appex"; sourceTree = BUILT_PRODUCTS_DIR; };
|
|
||||||
/* End PBXFileReference section */
|
/* End PBXFileReference section */
|
||||||
|
|
||||||
/* Begin PBXFileSystemSynchronizedBuildFileExceptionSet section */
|
/* Begin PBXFileSystemSynchronizedBuildFileExceptionSet section */
|
||||||
4C2F0C6D2E851BBD0033F5C2 /* Exceptions for "iOS (Share Extension)" folder in "iOS (Share Extension)" target */ = {
|
|
||||||
isa = PBXFileSystemSynchronizedBuildFileExceptionSet;
|
|
||||||
membershipExceptions = (
|
|
||||||
Info.plist,
|
|
||||||
);
|
|
||||||
target = 4C2F0C5D2E851BBD0033F5C2 /* iOS (Share Extension) */;
|
|
||||||
};
|
|
||||||
4C2F0C6F2E851BF90033F5C2 /* Exceptions for "Shared (App)" folder in "iOS (Share Extension)" target */ = {
|
|
||||||
isa = PBXFileSystemSynchronizedBuildFileExceptionSet;
|
|
||||||
membershipExceptions = (
|
|
||||||
Assets.xcassets,
|
|
||||||
HPAPI.m,
|
|
||||||
HPCredentialsHelper.m,
|
|
||||||
HPRPCClient.m,
|
|
||||||
"NSURL+HotPocketExtensions.m",
|
|
||||||
"Resources/icon-mac-384.png",
|
|
||||||
);
|
|
||||||
target = 4C2F0C5D2E851BBD0033F5C2 /* iOS (Share Extension) */;
|
|
||||||
};
|
|
||||||
4C3B958C2E83C83A00F4F82C /* Exceptions for "macOS (App)" folder in "HotPocket (macOS)" target */ = {
|
|
||||||
isa = PBXFileSystemSynchronizedBuildFileExceptionSet;
|
|
||||||
membershipExceptions = (
|
|
||||||
Info.plist,
|
|
||||||
);
|
|
||||||
target = 4CABCAC52E56F0C900D8A354 /* HotPocket (macOS) */;
|
|
||||||
};
|
|
||||||
4C7A01792E867D6200DEA460 /* Exceptions for "iOS (App)" folder in "iOS (Share Extension)" target */ = {
|
|
||||||
isa = PBXFileSystemSynchronizedBuildFileExceptionSet;
|
|
||||||
membershipExceptions = (
|
|
||||||
MultilineLabel.m,
|
|
||||||
);
|
|
||||||
target = 4C2F0C5D2E851BBD0033F5C2 /* iOS (Share Extension) */;
|
|
||||||
};
|
|
||||||
4CABCB042E56F0C900D8A354 /* Exceptions for "Shared (App)" folder in "HotPocket (iOS)" target */ = {
|
4CABCB042E56F0C900D8A354 /* Exceptions for "Shared (App)" folder in "HotPocket (iOS)" target */ = {
|
||||||
isa = PBXFileSystemSynchronizedBuildFileExceptionSet;
|
isa = PBXFileSystemSynchronizedBuildFileExceptionSet;
|
||||||
membershipExceptions = (
|
membershipExceptions = (
|
||||||
|
"/Localized: Resources/Main.html",
|
||||||
Assets.xcassets,
|
Assets.xcassets,
|
||||||
HPAPI.m,
|
|
||||||
HPAuthFlow.m,
|
|
||||||
HPCredentialsHelper.m,
|
|
||||||
HPRPCClient.m,
|
|
||||||
"NSURL+HotPocketExtensions.m",
|
|
||||||
"Resources/icon-mac-384.png",
|
"Resources/icon-mac-384.png",
|
||||||
|
Resources/Script.js,
|
||||||
|
Resources/Style.css,
|
||||||
|
ViewController.m,
|
||||||
);
|
);
|
||||||
target = 4CABCAAF2E56F0C900D8A354 /* HotPocket (iOS) */;
|
target = 4CABCAAF2E56F0C900D8A354 /* HotPocket (iOS) */;
|
||||||
};
|
};
|
||||||
|
@ -156,13 +90,12 @@
|
||||||
4CABCB0E2E56F0C900D8A354 /* Exceptions for "Shared (App)" folder in "HotPocket (macOS)" target */ = {
|
4CABCB0E2E56F0C900D8A354 /* Exceptions for "Shared (App)" folder in "HotPocket (macOS)" target */ = {
|
||||||
isa = PBXFileSystemSynchronizedBuildFileExceptionSet;
|
isa = PBXFileSystemSynchronizedBuildFileExceptionSet;
|
||||||
membershipExceptions = (
|
membershipExceptions = (
|
||||||
|
"/Localized: Resources/Main.html",
|
||||||
Assets.xcassets,
|
Assets.xcassets,
|
||||||
HPAPI.m,
|
|
||||||
HPAuthFlow.m,
|
|
||||||
HPCredentialsHelper.m,
|
|
||||||
HPRPCClient.m,
|
|
||||||
"NSURL+HotPocketExtensions.m",
|
|
||||||
"Resources/icon-mac-384.png",
|
"Resources/icon-mac-384.png",
|
||||||
|
Resources/Script.js,
|
||||||
|
Resources/Style.css,
|
||||||
|
ViewController.m,
|
||||||
);
|
);
|
||||||
target = 4CABCAC52E56F0C900D8A354 /* HotPocket (macOS) */;
|
target = 4CABCAC52E56F0C900D8A354 /* HotPocket (macOS) */;
|
||||||
};
|
};
|
||||||
|
@ -201,43 +134,14 @@
|
||||||
);
|
);
|
||||||
target = 4CABCADE2E56F0C900D8A354 /* HotPocket Extension (macOS) */;
|
target = 4CABCADE2E56F0C900D8A354 /* HotPocket Extension (macOS) */;
|
||||||
};
|
};
|
||||||
4CBCEA612E81CB9500722009 /* Exceptions for "macOS (Share Extension)" folder in "macOS (Share Extension)" target */ = {
|
|
||||||
isa = PBXFileSystemSynchronizedBuildFileExceptionSet;
|
|
||||||
membershipExceptions = (
|
|
||||||
Info.plist,
|
|
||||||
);
|
|
||||||
target = 4CBCEA4E2E81CB9500722009 /* macOS (Share Extension) */;
|
|
||||||
};
|
|
||||||
4CBCEA632E81CBC800722009 /* Exceptions for "Shared (App)" folder in "macOS (Share Extension)" target */ = {
|
|
||||||
isa = PBXFileSystemSynchronizedBuildFileExceptionSet;
|
|
||||||
membershipExceptions = (
|
|
||||||
Assets.xcassets,
|
|
||||||
HPAPI.m,
|
|
||||||
HPCredentialsHelper.m,
|
|
||||||
HPRPCClient.m,
|
|
||||||
"NSURL+HotPocketExtensions.m",
|
|
||||||
"Resources/icon-mac-384.png",
|
|
||||||
);
|
|
||||||
target = 4CBCEA4E2E81CB9500722009 /* macOS (Share Extension) */;
|
|
||||||
};
|
|
||||||
/* End PBXFileSystemSynchronizedBuildFileExceptionSet section */
|
/* End PBXFileSystemSynchronizedBuildFileExceptionSet section */
|
||||||
|
|
||||||
/* Begin PBXFileSystemSynchronizedRootGroup section */
|
/* Begin PBXFileSystemSynchronizedRootGroup section */
|
||||||
4C2F0C5F2E851BBD0033F5C2 /* iOS (Share Extension) */ = {
|
|
||||||
isa = PBXFileSystemSynchronizedRootGroup;
|
|
||||||
exceptions = (
|
|
||||||
4C2F0C6D2E851BBD0033F5C2 /* Exceptions for "iOS (Share Extension)" folder in "iOS (Share Extension)" target */,
|
|
||||||
);
|
|
||||||
path = "iOS (Share Extension)";
|
|
||||||
sourceTree = "<group>";
|
|
||||||
};
|
|
||||||
4CABCA962E56F0C800D8A354 /* Shared (App) */ = {
|
4CABCA962E56F0C800D8A354 /* Shared (App) */ = {
|
||||||
isa = PBXFileSystemSynchronizedRootGroup;
|
isa = PBXFileSystemSynchronizedRootGroup;
|
||||||
exceptions = (
|
exceptions = (
|
||||||
4CABCB042E56F0C900D8A354 /* Exceptions for "Shared (App)" folder in "HotPocket (iOS)" target */,
|
4CABCB042E56F0C900D8A354 /* Exceptions for "Shared (App)" folder in "HotPocket (iOS)" target */,
|
||||||
4CABCB0E2E56F0C900D8A354 /* Exceptions for "Shared (App)" folder in "HotPocket (macOS)" target */,
|
4CABCB0E2E56F0C900D8A354 /* Exceptions for "Shared (App)" folder in "HotPocket (macOS)" target */,
|
||||||
4CBCEA632E81CBC800722009 /* Exceptions for "Shared (App)" folder in "macOS (Share Extension)" target */,
|
|
||||||
4C2F0C6F2E851BF90033F5C2 /* Exceptions for "Shared (App)" folder in "iOS (Share Extension)" target */,
|
|
||||||
);
|
);
|
||||||
path = "Shared (App)";
|
path = "Shared (App)";
|
||||||
sourceTree = "<group>";
|
sourceTree = "<group>";
|
||||||
|
@ -259,16 +163,12 @@
|
||||||
isa = PBXFileSystemSynchronizedRootGroup;
|
isa = PBXFileSystemSynchronizedRootGroup;
|
||||||
exceptions = (
|
exceptions = (
|
||||||
4CABCB0D2E56F0C900D8A354 /* Exceptions for "iOS (App)" folder in "HotPocket (iOS)" target */,
|
4CABCB0D2E56F0C900D8A354 /* Exceptions for "iOS (App)" folder in "HotPocket (iOS)" target */,
|
||||||
4C7A01792E867D6200DEA460 /* Exceptions for "iOS (App)" folder in "iOS (Share Extension)" target */,
|
|
||||||
);
|
);
|
||||||
path = "iOS (App)";
|
path = "iOS (App)";
|
||||||
sourceTree = "<group>";
|
sourceTree = "<group>";
|
||||||
};
|
};
|
||||||
4CABCAC72E56F0C900D8A354 /* macOS (App) */ = {
|
4CABCAC72E56F0C900D8A354 /* macOS (App) */ = {
|
||||||
isa = PBXFileSystemSynchronizedRootGroup;
|
isa = PBXFileSystemSynchronizedRootGroup;
|
||||||
exceptions = (
|
|
||||||
4C3B958C2E83C83A00F4F82C /* Exceptions for "macOS (App)" folder in "HotPocket (macOS)" target */,
|
|
||||||
);
|
|
||||||
path = "macOS (App)";
|
path = "macOS (App)";
|
||||||
sourceTree = "<group>";
|
sourceTree = "<group>";
|
||||||
};
|
};
|
||||||
|
@ -288,24 +188,9 @@
|
||||||
path = "macOS (Extension)";
|
path = "macOS (Extension)";
|
||||||
sourceTree = "<group>";
|
sourceTree = "<group>";
|
||||||
};
|
};
|
||||||
4CBCEA502E81CB9500722009 /* macOS (Share Extension) */ = {
|
|
||||||
isa = PBXFileSystemSynchronizedRootGroup;
|
|
||||||
exceptions = (
|
|
||||||
4CBCEA612E81CB9500722009 /* Exceptions for "macOS (Share Extension)" folder in "macOS (Share Extension)" target */,
|
|
||||||
);
|
|
||||||
path = "macOS (Share Extension)";
|
|
||||||
sourceTree = "<group>";
|
|
||||||
};
|
|
||||||
/* End PBXFileSystemSynchronizedRootGroup section */
|
/* End PBXFileSystemSynchronizedRootGroup section */
|
||||||
|
|
||||||
/* Begin PBXFrameworksBuildPhase section */
|
/* Begin PBXFrameworksBuildPhase section */
|
||||||
4C2F0C5B2E851BBD0033F5C2 /* Frameworks */ = {
|
|
||||||
isa = PBXFrameworksBuildPhase;
|
|
||||||
buildActionMask = 2147483647;
|
|
||||||
files = (
|
|
||||||
);
|
|
||||||
runOnlyForDeploymentPostprocessing = 0;
|
|
||||||
};
|
|
||||||
4CABCAAD2E56F0C900D8A354 /* Frameworks */ = {
|
4CABCAAD2E56F0C900D8A354 /* Frameworks */ = {
|
||||||
isa = PBXFrameworksBuildPhase;
|
isa = PBXFrameworksBuildPhase;
|
||||||
buildActionMask = 2147483647;
|
buildActionMask = 2147483647;
|
||||||
|
@ -334,49 +219,18 @@
|
||||||
);
|
);
|
||||||
runOnlyForDeploymentPostprocessing = 0;
|
runOnlyForDeploymentPostprocessing = 0;
|
||||||
};
|
};
|
||||||
4CBCEA4C2E81CB9500722009 /* Frameworks */ = {
|
|
||||||
isa = PBXFrameworksBuildPhase;
|
|
||||||
buildActionMask = 2147483647;
|
|
||||||
files = (
|
|
||||||
);
|
|
||||||
runOnlyForDeploymentPostprocessing = 0;
|
|
||||||
};
|
|
||||||
/* End PBXFrameworksBuildPhase section */
|
/* End PBXFrameworksBuildPhase section */
|
||||||
|
|
||||||
/* Begin PBXGroup section */
|
/* Begin PBXGroup section */
|
||||||
4C11591F2E8B055F003B34AD /* Frameworks */ = {
|
|
||||||
isa = PBXGroup;
|
|
||||||
children = (
|
|
||||||
);
|
|
||||||
name = Frameworks;
|
|
||||||
sourceTree = "<group>";
|
|
||||||
};
|
|
||||||
4C70F30A2E8869D200320048 /* Shared (Share Extension) */ = {
|
|
||||||
isa = PBXGroup;
|
|
||||||
children = (
|
|
||||||
4C70F30B2E8869FB00320048 /* HPShareExtensionHelper.h */,
|
|
||||||
4C70F30C2E8869FB00320048 /* HPShareExtensionHelper.m */,
|
|
||||||
4C70F3132E886A8F00320048 /* HPSharedItem.h */,
|
|
||||||
4C70F3142E886A8F00320048 /* HPSharedItem.m */,
|
|
||||||
4C70F3172E886ADD00320048 /* HPSharedItemsContainer.h */,
|
|
||||||
4C70F3182E886ADD00320048 /* HPSharedItemsContainer.m */,
|
|
||||||
);
|
|
||||||
path = "Shared (Share Extension)";
|
|
||||||
sourceTree = "<group>";
|
|
||||||
};
|
|
||||||
4CABCA912E56F0C800D8A354 = {
|
4CABCA912E56F0C800D8A354 = {
|
||||||
isa = PBXGroup;
|
isa = PBXGroup;
|
||||||
children = (
|
children = (
|
||||||
4CABCA962E56F0C800D8A354 /* Shared (App) */,
|
4CABCA962E56F0C800D8A354 /* Shared (App) */,
|
||||||
4CABCAA02E56F0C900D8A354 /* Shared (Extension) */,
|
4CABCAA02E56F0C900D8A354 /* Shared (Extension) */,
|
||||||
4C70F30A2E8869D200320048 /* Shared (Share Extension) */,
|
|
||||||
4CABCAB22E56F0C900D8A354 /* iOS (App) */,
|
4CABCAB22E56F0C900D8A354 /* iOS (App) */,
|
||||||
4CABCAC72E56F0C900D8A354 /* macOS (App) */,
|
4CABCAC72E56F0C900D8A354 /* macOS (App) */,
|
||||||
4CABCAD92E56F0C900D8A354 /* iOS (Extension) */,
|
4CABCAD92E56F0C900D8A354 /* iOS (Extension) */,
|
||||||
4CABCAE32E56F0C900D8A354 /* macOS (Extension) */,
|
4CABCAE32E56F0C900D8A354 /* macOS (Extension) */,
|
||||||
4CBCEA502E81CB9500722009 /* macOS (Share Extension) */,
|
|
||||||
4C2F0C5F2E851BBD0033F5C2 /* iOS (Share Extension) */,
|
|
||||||
4C11591F2E8B055F003B34AD /* Frameworks */,
|
|
||||||
4CABCAB12E56F0C900D8A354 /* Products */,
|
4CABCAB12E56F0C900D8A354 /* Products */,
|
||||||
);
|
);
|
||||||
sourceTree = "<group>";
|
sourceTree = "<group>";
|
||||||
|
@ -388,8 +242,6 @@
|
||||||
4CABCAC62E56F0C900D8A354 /* HotPocket.app */,
|
4CABCAC62E56F0C900D8A354 /* HotPocket.app */,
|
||||||
4CABCAD52E56F0C900D8A354 /* HotPocket Extension.appex */,
|
4CABCAD52E56F0C900D8A354 /* HotPocket Extension.appex */,
|
||||||
4CABCADF2E56F0C900D8A354 /* HotPocket Extension.appex */,
|
4CABCADF2E56F0C900D8A354 /* HotPocket Extension.appex */,
|
||||||
4CBCEA4F2E81CB9500722009 /* Save to HotPocket.appex */,
|
|
||||||
4C2F0C5E2E851BBD0033F5C2 /* Save to HotPocket.appex */,
|
|
||||||
);
|
);
|
||||||
name = Products;
|
name = Products;
|
||||||
sourceTree = "<group>";
|
sourceTree = "<group>";
|
||||||
|
@ -397,28 +249,6 @@
|
||||||
/* End PBXGroup section */
|
/* End PBXGroup section */
|
||||||
|
|
||||||
/* Begin PBXNativeTarget section */
|
/* Begin PBXNativeTarget section */
|
||||||
4C2F0C5D2E851BBD0033F5C2 /* iOS (Share Extension) */ = {
|
|
||||||
isa = PBXNativeTarget;
|
|
||||||
buildConfigurationList = 4C2F0C6A2E851BBD0033F5C2 /* Build configuration list for PBXNativeTarget "iOS (Share Extension)" */;
|
|
||||||
buildPhases = (
|
|
||||||
4C2F0C5A2E851BBD0033F5C2 /* Sources */,
|
|
||||||
4C2F0C5B2E851BBD0033F5C2 /* Frameworks */,
|
|
||||||
4C2F0C5C2E851BBD0033F5C2 /* Resources */,
|
|
||||||
);
|
|
||||||
buildRules = (
|
|
||||||
);
|
|
||||||
dependencies = (
|
|
||||||
);
|
|
||||||
fileSystemSynchronizedGroups = (
|
|
||||||
4C2F0C5F2E851BBD0033F5C2 /* iOS (Share Extension) */,
|
|
||||||
);
|
|
||||||
name = "iOS (Share Extension)";
|
|
||||||
packageProductDependencies = (
|
|
||||||
);
|
|
||||||
productName = "iOS (Share Extension)";
|
|
||||||
productReference = 4C2F0C5E2E851BBD0033F5C2 /* Save to HotPocket.appex */;
|
|
||||||
productType = "com.apple.product-type.app-extension";
|
|
||||||
};
|
|
||||||
4CABCAAF2E56F0C900D8A354 /* HotPocket (iOS) */ = {
|
4CABCAAF2E56F0C900D8A354 /* HotPocket (iOS) */ = {
|
||||||
isa = PBXNativeTarget;
|
isa = PBXNativeTarget;
|
||||||
buildConfigurationList = 4CABCB0A2E56F0C900D8A354 /* Build configuration list for PBXNativeTarget "HotPocket (iOS)" */;
|
buildConfigurationList = 4CABCB0A2E56F0C900D8A354 /* Build configuration list for PBXNativeTarget "HotPocket (iOS)" */;
|
||||||
|
@ -432,7 +262,6 @@
|
||||||
);
|
);
|
||||||
dependencies = (
|
dependencies = (
|
||||||
4CABCAD82E56F0C900D8A354 /* PBXTargetDependency */,
|
4CABCAD82E56F0C900D8A354 /* PBXTargetDependency */,
|
||||||
4C2F0C682E851BBD0033F5C2 /* PBXTargetDependency */,
|
|
||||||
);
|
);
|
||||||
fileSystemSynchronizedGroups = (
|
fileSystemSynchronizedGroups = (
|
||||||
4CABCAB22E56F0C900D8A354 /* iOS (App) */,
|
4CABCAB22E56F0C900D8A354 /* iOS (App) */,
|
||||||
|
@ -457,7 +286,6 @@
|
||||||
);
|
);
|
||||||
dependencies = (
|
dependencies = (
|
||||||
4CABCAE22E56F0C900D8A354 /* PBXTargetDependency */,
|
4CABCAE22E56F0C900D8A354 /* PBXTargetDependency */,
|
||||||
4C1159222E8B055F003B34AD /* PBXTargetDependency */,
|
|
||||||
);
|
);
|
||||||
fileSystemSynchronizedGroups = (
|
fileSystemSynchronizedGroups = (
|
||||||
4CABCAC72E56F0C900D8A354 /* macOS (App) */,
|
4CABCAC72E56F0C900D8A354 /* macOS (App) */,
|
||||||
|
@ -513,28 +341,6 @@
|
||||||
productReference = 4CABCADF2E56F0C900D8A354 /* HotPocket Extension.appex */;
|
productReference = 4CABCADF2E56F0C900D8A354 /* HotPocket Extension.appex */;
|
||||||
productType = "com.apple.product-type.app-extension";
|
productType = "com.apple.product-type.app-extension";
|
||||||
};
|
};
|
||||||
4CBCEA4E2E81CB9500722009 /* macOS (Share Extension) */ = {
|
|
||||||
isa = PBXNativeTarget;
|
|
||||||
buildConfigurationList = 4CBCEA602E81CB9500722009 /* Build configuration list for PBXNativeTarget "macOS (Share Extension)" */;
|
|
||||||
buildPhases = (
|
|
||||||
4CBCEA4B2E81CB9500722009 /* Sources */,
|
|
||||||
4CBCEA4C2E81CB9500722009 /* Frameworks */,
|
|
||||||
4CBCEA4D2E81CB9500722009 /* Resources */,
|
|
||||||
);
|
|
||||||
buildRules = (
|
|
||||||
);
|
|
||||||
dependencies = (
|
|
||||||
);
|
|
||||||
fileSystemSynchronizedGroups = (
|
|
||||||
4CBCEA502E81CB9500722009 /* macOS (Share Extension) */,
|
|
||||||
);
|
|
||||||
name = "macOS (Share Extension)";
|
|
||||||
packageProductDependencies = (
|
|
||||||
);
|
|
||||||
productName = "macOS (Share Extension)";
|
|
||||||
productReference = 4CBCEA4F2E81CB9500722009 /* Save to HotPocket.appex */;
|
|
||||||
productType = "com.apple.product-type.app-extension";
|
|
||||||
};
|
|
||||||
/* End PBXNativeTarget section */
|
/* End PBXNativeTarget section */
|
||||||
|
|
||||||
/* Begin PBXProject section */
|
/* Begin PBXProject section */
|
||||||
|
@ -544,9 +350,6 @@
|
||||||
BuildIndependentTargetsInParallel = 1;
|
BuildIndependentTargetsInParallel = 1;
|
||||||
LastUpgradeCheck = 1640;
|
LastUpgradeCheck = 1640;
|
||||||
TargetAttributes = {
|
TargetAttributes = {
|
||||||
4C2F0C5D2E851BBD0033F5C2 = {
|
|
||||||
CreatedOnToolsVersion = 26.0;
|
|
||||||
};
|
|
||||||
4CABCAAF2E56F0C900D8A354 = {
|
4CABCAAF2E56F0C900D8A354 = {
|
||||||
CreatedOnToolsVersion = 16.4;
|
CreatedOnToolsVersion = 16.4;
|
||||||
};
|
};
|
||||||
|
@ -559,9 +362,6 @@
|
||||||
4CABCADE2E56F0C900D8A354 = {
|
4CABCADE2E56F0C900D8A354 = {
|
||||||
CreatedOnToolsVersion = 16.4;
|
CreatedOnToolsVersion = 16.4;
|
||||||
};
|
};
|
||||||
4CBCEA4E2E81CB9500722009 = {
|
|
||||||
CreatedOnToolsVersion = 16.4;
|
|
||||||
};
|
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
buildConfigurationList = 4CABCA952E56F0C800D8A354 /* Build configuration list for PBXProject "HotPocket" */;
|
buildConfigurationList = 4CABCA952E56F0C800D8A354 /* Build configuration list for PBXProject "HotPocket" */;
|
||||||
|
@ -582,20 +382,11 @@
|
||||||
4CABCAC52E56F0C900D8A354 /* HotPocket (macOS) */,
|
4CABCAC52E56F0C900D8A354 /* HotPocket (macOS) */,
|
||||||
4CABCAD42E56F0C900D8A354 /* HotPocket Extension (iOS) */,
|
4CABCAD42E56F0C900D8A354 /* HotPocket Extension (iOS) */,
|
||||||
4CABCADE2E56F0C900D8A354 /* HotPocket Extension (macOS) */,
|
4CABCADE2E56F0C900D8A354 /* HotPocket Extension (macOS) */,
|
||||||
4CBCEA4E2E81CB9500722009 /* macOS (Share Extension) */,
|
|
||||||
4C2F0C5D2E851BBD0033F5C2 /* iOS (Share Extension) */,
|
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
/* End PBXProject section */
|
/* End PBXProject section */
|
||||||
|
|
||||||
/* Begin PBXResourcesBuildPhase section */
|
/* Begin PBXResourcesBuildPhase section */
|
||||||
4C2F0C5C2E851BBD0033F5C2 /* Resources */ = {
|
|
||||||
isa = PBXResourcesBuildPhase;
|
|
||||||
buildActionMask = 2147483647;
|
|
||||||
files = (
|
|
||||||
);
|
|
||||||
runOnlyForDeploymentPostprocessing = 0;
|
|
||||||
};
|
|
||||||
4CABCAAE2E56F0C900D8A354 /* Resources */ = {
|
4CABCAAE2E56F0C900D8A354 /* Resources */ = {
|
||||||
isa = PBXResourcesBuildPhase;
|
isa = PBXResourcesBuildPhase;
|
||||||
buildActionMask = 2147483647;
|
buildActionMask = 2147483647;
|
||||||
|
@ -624,26 +415,9 @@
|
||||||
);
|
);
|
||||||
runOnlyForDeploymentPostprocessing = 0;
|
runOnlyForDeploymentPostprocessing = 0;
|
||||||
};
|
};
|
||||||
4CBCEA4D2E81CB9500722009 /* Resources */ = {
|
|
||||||
isa = PBXResourcesBuildPhase;
|
|
||||||
buildActionMask = 2147483647;
|
|
||||||
files = (
|
|
||||||
);
|
|
||||||
runOnlyForDeploymentPostprocessing = 0;
|
|
||||||
};
|
|
||||||
/* End PBXResourcesBuildPhase section */
|
/* End PBXResourcesBuildPhase section */
|
||||||
|
|
||||||
/* Begin PBXSourcesBuildPhase section */
|
/* Begin PBXSourcesBuildPhase section */
|
||||||
4C2F0C5A2E851BBD0033F5C2 /* Sources */ = {
|
|
||||||
isa = PBXSourcesBuildPhase;
|
|
||||||
buildActionMask = 2147483647;
|
|
||||||
files = (
|
|
||||||
4C70F30E2E8869FB00320048 /* HPShareExtensionHelper.m in Sources */,
|
|
||||||
4C70F3152E886A8F00320048 /* HPSharedItem.m in Sources */,
|
|
||||||
4C70F3192E886ADD00320048 /* HPSharedItemsContainer.m in Sources */,
|
|
||||||
);
|
|
||||||
runOnlyForDeploymentPostprocessing = 0;
|
|
||||||
};
|
|
||||||
4CABCAAC2E56F0C900D8A354 /* Sources */ = {
|
4CABCAAC2E56F0C900D8A354 /* Sources */ = {
|
||||||
isa = PBXSourcesBuildPhase;
|
isa = PBXSourcesBuildPhase;
|
||||||
buildActionMask = 2147483647;
|
buildActionMask = 2147483647;
|
||||||
|
@ -672,29 +446,9 @@
|
||||||
);
|
);
|
||||||
runOnlyForDeploymentPostprocessing = 0;
|
runOnlyForDeploymentPostprocessing = 0;
|
||||||
};
|
};
|
||||||
4CBCEA4B2E81CB9500722009 /* Sources */ = {
|
|
||||||
isa = PBXSourcesBuildPhase;
|
|
||||||
buildActionMask = 2147483647;
|
|
||||||
files = (
|
|
||||||
4C70F3162E886A8F00320048 /* HPSharedItem.m in Sources */,
|
|
||||||
4C70F30D2E8869FB00320048 /* HPShareExtensionHelper.m in Sources */,
|
|
||||||
4C70F31A2E886ADD00320048 /* HPSharedItemsContainer.m in Sources */,
|
|
||||||
);
|
|
||||||
runOnlyForDeploymentPostprocessing = 0;
|
|
||||||
};
|
|
||||||
/* End PBXSourcesBuildPhase section */
|
/* End PBXSourcesBuildPhase section */
|
||||||
|
|
||||||
/* Begin PBXTargetDependency section */
|
/* Begin PBXTargetDependency section */
|
||||||
4C1159222E8B055F003B34AD /* PBXTargetDependency */ = {
|
|
||||||
isa = PBXTargetDependency;
|
|
||||||
target = 4CBCEA4E2E81CB9500722009 /* macOS (Share Extension) */;
|
|
||||||
targetProxy = 4C1159212E8B055F003B34AD /* PBXContainerItemProxy */;
|
|
||||||
};
|
|
||||||
4C2F0C682E851BBD0033F5C2 /* PBXTargetDependency */ = {
|
|
||||||
isa = PBXTargetDependency;
|
|
||||||
target = 4C2F0C5D2E851BBD0033F5C2 /* iOS (Share Extension) */;
|
|
||||||
targetProxy = 4C2F0C672E851BBD0033F5C2 /* PBXContainerItemProxy */;
|
|
||||||
};
|
|
||||||
4CABCAD82E56F0C900D8A354 /* PBXTargetDependency */ = {
|
4CABCAD82E56F0C900D8A354 /* PBXTargetDependency */ = {
|
||||||
isa = PBXTargetDependency;
|
isa = PBXTargetDependency;
|
||||||
target = 4CABCAD42E56F0C900D8A354 /* HotPocket Extension (iOS) */;
|
target = 4CABCAD42E56F0C900D8A354 /* HotPocket Extension (iOS) */;
|
||||||
|
@ -708,83 +462,15 @@
|
||||||
/* End PBXTargetDependency section */
|
/* End PBXTargetDependency section */
|
||||||
|
|
||||||
/* Begin XCBuildConfiguration section */
|
/* Begin XCBuildConfiguration section */
|
||||||
4C2F0C6B2E851BBD0033F5C2 /* Debug */ = {
|
|
||||||
isa = XCBuildConfiguration;
|
|
||||||
buildSettings = {
|
|
||||||
CODE_SIGN_ENTITLEMENTS = "iOS (Share Extension)/iOS (Share Extension).entitlements";
|
|
||||||
CODE_SIGN_STYLE = Automatic;
|
|
||||||
CURRENT_PROJECT_VERSION = 2025102101;
|
|
||||||
DEVELOPMENT_TEAM = 648728X64K;
|
|
||||||
GENERATE_INFOPLIST_FILE = YES;
|
|
||||||
INFOPLIST_FILE = "iOS (Share Extension)/Info.plist";
|
|
||||||
INFOPLIST_KEY_CFBundleDisplayName = "Save to HotPocket";
|
|
||||||
INFOPLIST_KEY_ITSAppUsesNonExemptEncryption = NO;
|
|
||||||
INFOPLIST_KEY_NSHumanReadableCopyright = "Copyright © 2025-present BTHLabs";
|
|
||||||
IPHONEOS_DEPLOYMENT_TARGET = 18.0;
|
|
||||||
LD_RUNPATH_SEARCH_PATHS = (
|
|
||||||
"$(inherited)",
|
|
||||||
"@executable_path/Frameworks",
|
|
||||||
"@executable_path/../../Frameworks",
|
|
||||||
);
|
|
||||||
MARKETING_VERSION = 25.10.21;
|
|
||||||
PRODUCT_BUNDLE_IDENTIFIER = pl.bthlabs.HotPocket.ShareExtension;
|
|
||||||
PRODUCT_NAME = "Save to HotPocket";
|
|
||||||
SDKROOT = iphoneos;
|
|
||||||
SKIP_INSTALL = YES;
|
|
||||||
STRING_CATALOG_GENERATE_SYMBOLS = YES;
|
|
||||||
SUPPORTED_PLATFORMS = "iphoneos iphonesimulator";
|
|
||||||
SUPPORTS_MACCATALYST = NO;
|
|
||||||
SUPPORTS_MAC_DESIGNED_FOR_IPHONE_IPAD = NO;
|
|
||||||
SUPPORTS_XR_DESIGNED_FOR_IPHONE_IPAD = NO;
|
|
||||||
SWIFT_EMIT_LOC_STRINGS = YES;
|
|
||||||
TARGETED_DEVICE_FAMILY = "1,2";
|
|
||||||
};
|
|
||||||
name = Debug;
|
|
||||||
};
|
|
||||||
4C2F0C6C2E851BBD0033F5C2 /* Release */ = {
|
|
||||||
isa = XCBuildConfiguration;
|
|
||||||
buildSettings = {
|
|
||||||
CODE_SIGN_ENTITLEMENTS = "iOS (Share Extension)/iOS (Share Extension).entitlements";
|
|
||||||
CODE_SIGN_STYLE = Automatic;
|
|
||||||
CURRENT_PROJECT_VERSION = 2025102101;
|
|
||||||
DEVELOPMENT_TEAM = 648728X64K;
|
|
||||||
GENERATE_INFOPLIST_FILE = YES;
|
|
||||||
INFOPLIST_FILE = "iOS (Share Extension)/Info.plist";
|
|
||||||
INFOPLIST_KEY_CFBundleDisplayName = "Save to HotPocket";
|
|
||||||
INFOPLIST_KEY_ITSAppUsesNonExemptEncryption = NO;
|
|
||||||
INFOPLIST_KEY_NSHumanReadableCopyright = "Copyright © 2025-present BTHLabs";
|
|
||||||
IPHONEOS_DEPLOYMENT_TARGET = 18.0;
|
|
||||||
LD_RUNPATH_SEARCH_PATHS = (
|
|
||||||
"$(inherited)",
|
|
||||||
"@executable_path/Frameworks",
|
|
||||||
"@executable_path/../../Frameworks",
|
|
||||||
);
|
|
||||||
MARKETING_VERSION = 25.10.21;
|
|
||||||
PRODUCT_BUNDLE_IDENTIFIER = pl.bthlabs.HotPocket.ShareExtension;
|
|
||||||
PRODUCT_NAME = "Save to HotPocket";
|
|
||||||
SDKROOT = iphoneos;
|
|
||||||
SKIP_INSTALL = YES;
|
|
||||||
STRING_CATALOG_GENERATE_SYMBOLS = YES;
|
|
||||||
SUPPORTED_PLATFORMS = "iphoneos iphonesimulator";
|
|
||||||
SUPPORTS_MACCATALYST = NO;
|
|
||||||
SUPPORTS_MAC_DESIGNED_FOR_IPHONE_IPAD = NO;
|
|
||||||
SUPPORTS_XR_DESIGNED_FOR_IPHONE_IPAD = NO;
|
|
||||||
SWIFT_EMIT_LOC_STRINGS = YES;
|
|
||||||
TARGETED_DEVICE_FAMILY = "1,2";
|
|
||||||
VALIDATE_PRODUCT = YES;
|
|
||||||
};
|
|
||||||
name = Release;
|
|
||||||
};
|
|
||||||
4CABCB062E56F0C900D8A354 /* Debug */ = {
|
4CABCB062E56F0C900D8A354 /* Debug */ = {
|
||||||
isa = XCBuildConfiguration;
|
isa = XCBuildConfiguration;
|
||||||
buildSettings = {
|
buildSettings = {
|
||||||
CODE_SIGN_STYLE = Automatic;
|
CODE_SIGN_STYLE = Automatic;
|
||||||
CURRENT_PROJECT_VERSION = 2025102101;
|
CURRENT_PROJECT_VERSION = 2025091701;
|
||||||
DEVELOPMENT_TEAM = 648728X64K;
|
DEVELOPMENT_TEAM = 648728X64K;
|
||||||
GENERATE_INFOPLIST_FILE = YES;
|
GENERATE_INFOPLIST_FILE = YES;
|
||||||
INFOPLIST_FILE = "iOS (Extension)/Info.plist";
|
INFOPLIST_FILE = "iOS (Extension)/Info.plist";
|
||||||
INFOPLIST_KEY_CFBundleDisplayName = HotPocket;
|
INFOPLIST_KEY_CFBundleDisplayName = HotPocket;
|
||||||
INFOPLIST_KEY_ITSAppUsesNonExemptEncryption = NO;
|
|
||||||
INFOPLIST_KEY_NSHumanReadableCopyright = "";
|
INFOPLIST_KEY_NSHumanReadableCopyright = "";
|
||||||
IPHONEOS_DEPLOYMENT_TARGET = 18.0;
|
IPHONEOS_DEPLOYMENT_TARGET = 18.0;
|
||||||
LD_RUNPATH_SEARCH_PATHS = (
|
LD_RUNPATH_SEARCH_PATHS = (
|
||||||
|
@ -792,7 +478,7 @@
|
||||||
"@executable_path/Frameworks",
|
"@executable_path/Frameworks",
|
||||||
"@executable_path/../../Frameworks",
|
"@executable_path/../../Frameworks",
|
||||||
);
|
);
|
||||||
MARKETING_VERSION = 25.10.21;
|
MARKETING_VERSION = 25.9.17;
|
||||||
OTHER_LDFLAGS = (
|
OTHER_LDFLAGS = (
|
||||||
"-framework",
|
"-framework",
|
||||||
SafariServices,
|
SafariServices,
|
||||||
|
@ -801,10 +487,6 @@
|
||||||
PRODUCT_NAME = "HotPocket Extension";
|
PRODUCT_NAME = "HotPocket Extension";
|
||||||
SDKROOT = iphoneos;
|
SDKROOT = iphoneos;
|
||||||
SKIP_INSTALL = YES;
|
SKIP_INSTALL = YES;
|
||||||
SUPPORTED_PLATFORMS = "iphoneos iphonesimulator";
|
|
||||||
SUPPORTS_MACCATALYST = NO;
|
|
||||||
SUPPORTS_MAC_DESIGNED_FOR_IPHONE_IPAD = NO;
|
|
||||||
SUPPORTS_XR_DESIGNED_FOR_IPHONE_IPAD = NO;
|
|
||||||
SWIFT_EMIT_LOC_STRINGS = YES;
|
SWIFT_EMIT_LOC_STRINGS = YES;
|
||||||
TARGETED_DEVICE_FAMILY = "1,2";
|
TARGETED_DEVICE_FAMILY = "1,2";
|
||||||
};
|
};
|
||||||
|
@ -814,12 +496,11 @@
|
||||||
isa = XCBuildConfiguration;
|
isa = XCBuildConfiguration;
|
||||||
buildSettings = {
|
buildSettings = {
|
||||||
CODE_SIGN_STYLE = Automatic;
|
CODE_SIGN_STYLE = Automatic;
|
||||||
CURRENT_PROJECT_VERSION = 2025102101;
|
CURRENT_PROJECT_VERSION = 2025091701;
|
||||||
DEVELOPMENT_TEAM = 648728X64K;
|
DEVELOPMENT_TEAM = 648728X64K;
|
||||||
GENERATE_INFOPLIST_FILE = YES;
|
GENERATE_INFOPLIST_FILE = YES;
|
||||||
INFOPLIST_FILE = "iOS (Extension)/Info.plist";
|
INFOPLIST_FILE = "iOS (Extension)/Info.plist";
|
||||||
INFOPLIST_KEY_CFBundleDisplayName = HotPocket;
|
INFOPLIST_KEY_CFBundleDisplayName = HotPocket;
|
||||||
INFOPLIST_KEY_ITSAppUsesNonExemptEncryption = NO;
|
|
||||||
INFOPLIST_KEY_NSHumanReadableCopyright = "";
|
INFOPLIST_KEY_NSHumanReadableCopyright = "";
|
||||||
IPHONEOS_DEPLOYMENT_TARGET = 18.0;
|
IPHONEOS_DEPLOYMENT_TARGET = 18.0;
|
||||||
LD_RUNPATH_SEARCH_PATHS = (
|
LD_RUNPATH_SEARCH_PATHS = (
|
||||||
|
@ -827,7 +508,7 @@
|
||||||
"@executable_path/Frameworks",
|
"@executable_path/Frameworks",
|
||||||
"@executable_path/../../Frameworks",
|
"@executable_path/../../Frameworks",
|
||||||
);
|
);
|
||||||
MARKETING_VERSION = 25.10.21;
|
MARKETING_VERSION = 25.9.17;
|
||||||
OTHER_LDFLAGS = (
|
OTHER_LDFLAGS = (
|
||||||
"-framework",
|
"-framework",
|
||||||
SafariServices,
|
SafariServices,
|
||||||
|
@ -836,10 +517,6 @@
|
||||||
PRODUCT_NAME = "HotPocket Extension";
|
PRODUCT_NAME = "HotPocket Extension";
|
||||||
SDKROOT = iphoneos;
|
SDKROOT = iphoneos;
|
||||||
SKIP_INSTALL = YES;
|
SKIP_INSTALL = YES;
|
||||||
SUPPORTED_PLATFORMS = "iphoneos iphonesimulator";
|
|
||||||
SUPPORTS_MACCATALYST = NO;
|
|
||||||
SUPPORTS_MAC_DESIGNED_FOR_IPHONE_IPAD = NO;
|
|
||||||
SUPPORTS_XR_DESIGNED_FOR_IPHONE_IPAD = NO;
|
|
||||||
SWIFT_EMIT_LOC_STRINGS = YES;
|
SWIFT_EMIT_LOC_STRINGS = YES;
|
||||||
TARGETED_DEVICE_FAMILY = "1,2";
|
TARGETED_DEVICE_FAMILY = "1,2";
|
||||||
VALIDATE_PRODUCT = YES;
|
VALIDATE_PRODUCT = YES;
|
||||||
|
@ -851,29 +528,24 @@
|
||||||
buildSettings = {
|
buildSettings = {
|
||||||
ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
|
ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
|
||||||
ASSETCATALOG_COMPILER_GLOBAL_ACCENT_COLOR_NAME = AccentColor;
|
ASSETCATALOG_COMPILER_GLOBAL_ACCENT_COLOR_NAME = AccentColor;
|
||||||
CODE_SIGN_ENTITLEMENTS = "iOS (App)/HotPocket (iOS).entitlements";
|
|
||||||
CODE_SIGN_STYLE = Automatic;
|
CODE_SIGN_STYLE = Automatic;
|
||||||
CURRENT_PROJECT_VERSION = 2025102101;
|
CURRENT_PROJECT_VERSION = 2025091701;
|
||||||
DEVELOPMENT_TEAM = 648728X64K;
|
DEVELOPMENT_TEAM = 648728X64K;
|
||||||
GENERATE_INFOPLIST_FILE = YES;
|
GENERATE_INFOPLIST_FILE = YES;
|
||||||
INFOPLIST_FILE = "iOS (App)/Info.plist";
|
INFOPLIST_FILE = "iOS (App)/Info.plist";
|
||||||
INFOPLIST_KEY_CFBundleDisplayName = HotPocket;
|
INFOPLIST_KEY_CFBundleDisplayName = HotPocket;
|
||||||
INFOPLIST_KEY_ITSAppUsesNonExemptEncryption = NO;
|
|
||||||
INFOPLIST_KEY_LSApplicationCategoryType = "public.app-category.utilities";
|
INFOPLIST_KEY_LSApplicationCategoryType = "public.app-category.utilities";
|
||||||
INFOPLIST_KEY_NSHumanReadableCopyright = "Copyright © 2025-present BTHLabs";
|
INFOPLIST_KEY_NSHumanReadableCopyright = "Copyright © 2025-present BTHLabs";
|
||||||
INFOPLIST_KEY_UIApplicationSupportsIndirectInputEvents = YES;
|
INFOPLIST_KEY_UIApplicationSupportsIndirectInputEvents = YES;
|
||||||
INFOPLIST_KEY_UILaunchStoryboardName = LaunchScreen;
|
INFOPLIST_KEY_UILaunchStoryboardName = LaunchScreen;
|
||||||
INFOPLIST_KEY_UIMainStoryboardFile = Main;
|
INFOPLIST_KEY_UIMainStoryboardFile = Main;
|
||||||
INFOPLIST_KEY_UIRequiresFullScreen = YES;
|
INFOPLIST_KEY_UISupportedInterfaceOrientations = "UIInterfaceOrientationLandscapeLeft UIInterfaceOrientationLandscapeRight UIInterfaceOrientationPortrait UIInterfaceOrientationPortraitUpsideDown";
|
||||||
INFOPLIST_KEY_UIStatusBarStyle = UIStatusBarStyleLightContent;
|
|
||||||
INFOPLIST_KEY_UISupportedInterfaceOrientations = UIInterfaceOrientationPortrait;
|
|
||||||
INFOPLIST_KEY_UISupportedInterfaceOrientations_iPad = "UIInterfaceOrientationLandscapeLeft UIInterfaceOrientationLandscapeRight UIInterfaceOrientationPortrait UIInterfaceOrientationPortraitUpsideDown";
|
|
||||||
IPHONEOS_DEPLOYMENT_TARGET = 18.0;
|
IPHONEOS_DEPLOYMENT_TARGET = 18.0;
|
||||||
LD_RUNPATH_SEARCH_PATHS = (
|
LD_RUNPATH_SEARCH_PATHS = (
|
||||||
"$(inherited)",
|
"$(inherited)",
|
||||||
"@executable_path/Frameworks",
|
"@executable_path/Frameworks",
|
||||||
);
|
);
|
||||||
MARKETING_VERSION = 25.10.21;
|
MARKETING_VERSION = 25.9.17;
|
||||||
OTHER_LDFLAGS = (
|
OTHER_LDFLAGS = (
|
||||||
"-framework",
|
"-framework",
|
||||||
SafariServices,
|
SafariServices,
|
||||||
|
@ -897,29 +569,24 @@
|
||||||
buildSettings = {
|
buildSettings = {
|
||||||
ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
|
ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
|
||||||
ASSETCATALOG_COMPILER_GLOBAL_ACCENT_COLOR_NAME = AccentColor;
|
ASSETCATALOG_COMPILER_GLOBAL_ACCENT_COLOR_NAME = AccentColor;
|
||||||
CODE_SIGN_ENTITLEMENTS = "iOS (App)/HotPocket (iOS).entitlements";
|
|
||||||
CODE_SIGN_STYLE = Automatic;
|
CODE_SIGN_STYLE = Automatic;
|
||||||
CURRENT_PROJECT_VERSION = 2025102101;
|
CURRENT_PROJECT_VERSION = 2025091701;
|
||||||
DEVELOPMENT_TEAM = 648728X64K;
|
DEVELOPMENT_TEAM = 648728X64K;
|
||||||
GENERATE_INFOPLIST_FILE = YES;
|
GENERATE_INFOPLIST_FILE = YES;
|
||||||
INFOPLIST_FILE = "iOS (App)/Info.plist";
|
INFOPLIST_FILE = "iOS (App)/Info.plist";
|
||||||
INFOPLIST_KEY_CFBundleDisplayName = HotPocket;
|
INFOPLIST_KEY_CFBundleDisplayName = HotPocket;
|
||||||
INFOPLIST_KEY_ITSAppUsesNonExemptEncryption = NO;
|
|
||||||
INFOPLIST_KEY_LSApplicationCategoryType = "public.app-category.utilities";
|
INFOPLIST_KEY_LSApplicationCategoryType = "public.app-category.utilities";
|
||||||
INFOPLIST_KEY_NSHumanReadableCopyright = "Copyright © 2025-present BTHLabs";
|
INFOPLIST_KEY_NSHumanReadableCopyright = "Copyright © 2025-present BTHLabs";
|
||||||
INFOPLIST_KEY_UIApplicationSupportsIndirectInputEvents = YES;
|
INFOPLIST_KEY_UIApplicationSupportsIndirectInputEvents = YES;
|
||||||
INFOPLIST_KEY_UILaunchStoryboardName = LaunchScreen;
|
INFOPLIST_KEY_UILaunchStoryboardName = LaunchScreen;
|
||||||
INFOPLIST_KEY_UIMainStoryboardFile = Main;
|
INFOPLIST_KEY_UIMainStoryboardFile = Main;
|
||||||
INFOPLIST_KEY_UIRequiresFullScreen = YES;
|
INFOPLIST_KEY_UISupportedInterfaceOrientations = "UIInterfaceOrientationLandscapeLeft UIInterfaceOrientationLandscapeRight UIInterfaceOrientationPortrait UIInterfaceOrientationPortraitUpsideDown";
|
||||||
INFOPLIST_KEY_UIStatusBarStyle = UIStatusBarStyleLightContent;
|
|
||||||
INFOPLIST_KEY_UISupportedInterfaceOrientations = UIInterfaceOrientationPortrait;
|
|
||||||
INFOPLIST_KEY_UISupportedInterfaceOrientations_iPad = "UIInterfaceOrientationLandscapeLeft UIInterfaceOrientationLandscapeRight UIInterfaceOrientationPortrait UIInterfaceOrientationPortraitUpsideDown";
|
|
||||||
IPHONEOS_DEPLOYMENT_TARGET = 18.0;
|
IPHONEOS_DEPLOYMENT_TARGET = 18.0;
|
||||||
LD_RUNPATH_SEARCH_PATHS = (
|
LD_RUNPATH_SEARCH_PATHS = (
|
||||||
"$(inherited)",
|
"$(inherited)",
|
||||||
"@executable_path/Frameworks",
|
"@executable_path/Frameworks",
|
||||||
);
|
);
|
||||||
MARKETING_VERSION = 25.10.21;
|
MARKETING_VERSION = 25.9.17;
|
||||||
OTHER_LDFLAGS = (
|
OTHER_LDFLAGS = (
|
||||||
"-framework",
|
"-framework",
|
||||||
SafariServices,
|
SafariServices,
|
||||||
|
@ -943,31 +610,29 @@
|
||||||
isa = XCBuildConfiguration;
|
isa = XCBuildConfiguration;
|
||||||
buildSettings = {
|
buildSettings = {
|
||||||
CODE_SIGN_ENTITLEMENTS = "macOS (Extension)/HotPocket.entitlements";
|
CODE_SIGN_ENTITLEMENTS = "macOS (Extension)/HotPocket.entitlements";
|
||||||
"CODE_SIGN_IDENTITY[sdk=macosx*]" = "Apple Development";
|
"CODE_SIGN_IDENTITY[sdk=macosx*]" = "-";
|
||||||
CODE_SIGN_STYLE = Automatic;
|
CODE_SIGN_STYLE = Automatic;
|
||||||
CURRENT_PROJECT_VERSION = 2025102101;
|
CURRENT_PROJECT_VERSION = 2025091701;
|
||||||
DEVELOPMENT_TEAM = 648728X64K;
|
DEVELOPMENT_TEAM = 648728X64K;
|
||||||
ENABLE_HARDENED_RUNTIME = YES;
|
ENABLE_HARDENED_RUNTIME = YES;
|
||||||
ENABLE_USER_SCRIPT_SANDBOXING = NO;
|
ENABLE_USER_SCRIPT_SANDBOXING = NO;
|
||||||
GENERATE_INFOPLIST_FILE = YES;
|
GENERATE_INFOPLIST_FILE = YES;
|
||||||
INFOPLIST_FILE = "macOS (Extension)/Info.plist";
|
INFOPLIST_FILE = "macOS (Extension)/Info.plist";
|
||||||
INFOPLIST_KEY_CFBundleDisplayName = HotPocket;
|
INFOPLIST_KEY_CFBundleDisplayName = HotPocket;
|
||||||
INFOPLIST_KEY_ITSAppUsesNonExemptEncryption = NO;
|
|
||||||
INFOPLIST_KEY_NSHumanReadableCopyright = "";
|
INFOPLIST_KEY_NSHumanReadableCopyright = "";
|
||||||
LD_RUNPATH_SEARCH_PATHS = (
|
LD_RUNPATH_SEARCH_PATHS = (
|
||||||
"$(inherited)",
|
"$(inherited)",
|
||||||
"@executable_path/../Frameworks",
|
"@executable_path/../Frameworks",
|
||||||
"@executable_path/../../../../Frameworks",
|
"@executable_path/../../../../Frameworks",
|
||||||
);
|
);
|
||||||
MACOSX_DEPLOYMENT_TARGET = 15.0;
|
MACOSX_DEPLOYMENT_TARGET = 10.14;
|
||||||
MARKETING_VERSION = 25.10.21;
|
MARKETING_VERSION = 25.9.17;
|
||||||
OTHER_LDFLAGS = (
|
OTHER_LDFLAGS = (
|
||||||
"-framework",
|
"-framework",
|
||||||
SafariServices,
|
SafariServices,
|
||||||
);
|
);
|
||||||
PRODUCT_BUNDLE_IDENTIFIER = pl.bthlabs.HotPocket.Extension;
|
PRODUCT_BUNDLE_IDENTIFIER = pl.bthlabs.HotPocket.Extension;
|
||||||
PRODUCT_NAME = "HotPocket Extension";
|
PRODUCT_NAME = "HotPocket Extension";
|
||||||
REGISTER_APP_GROUPS = YES;
|
|
||||||
SDKROOT = macosx;
|
SDKROOT = macosx;
|
||||||
SKIP_INSTALL = YES;
|
SKIP_INSTALL = YES;
|
||||||
SWIFT_EMIT_LOC_STRINGS = YES;
|
SWIFT_EMIT_LOC_STRINGS = YES;
|
||||||
|
@ -980,29 +645,27 @@
|
||||||
CODE_SIGN_ENTITLEMENTS = "macOS (Extension)/HotPocket.entitlements";
|
CODE_SIGN_ENTITLEMENTS = "macOS (Extension)/HotPocket.entitlements";
|
||||||
"CODE_SIGN_IDENTITY[sdk=macosx*]" = "Apple Development";
|
"CODE_SIGN_IDENTITY[sdk=macosx*]" = "Apple Development";
|
||||||
CODE_SIGN_STYLE = Automatic;
|
CODE_SIGN_STYLE = Automatic;
|
||||||
CURRENT_PROJECT_VERSION = 2025102101;
|
CURRENT_PROJECT_VERSION = 2025091701;
|
||||||
DEVELOPMENT_TEAM = 648728X64K;
|
DEVELOPMENT_TEAM = 648728X64K;
|
||||||
ENABLE_HARDENED_RUNTIME = YES;
|
ENABLE_HARDENED_RUNTIME = YES;
|
||||||
ENABLE_USER_SCRIPT_SANDBOXING = NO;
|
ENABLE_USER_SCRIPT_SANDBOXING = NO;
|
||||||
GENERATE_INFOPLIST_FILE = YES;
|
GENERATE_INFOPLIST_FILE = YES;
|
||||||
INFOPLIST_FILE = "macOS (Extension)/Info.plist";
|
INFOPLIST_FILE = "macOS (Extension)/Info.plist";
|
||||||
INFOPLIST_KEY_CFBundleDisplayName = HotPocket;
|
INFOPLIST_KEY_CFBundleDisplayName = HotPocket;
|
||||||
INFOPLIST_KEY_ITSAppUsesNonExemptEncryption = NO;
|
|
||||||
INFOPLIST_KEY_NSHumanReadableCopyright = "";
|
INFOPLIST_KEY_NSHumanReadableCopyright = "";
|
||||||
LD_RUNPATH_SEARCH_PATHS = (
|
LD_RUNPATH_SEARCH_PATHS = (
|
||||||
"$(inherited)",
|
"$(inherited)",
|
||||||
"@executable_path/../Frameworks",
|
"@executable_path/../Frameworks",
|
||||||
"@executable_path/../../../../Frameworks",
|
"@executable_path/../../../../Frameworks",
|
||||||
);
|
);
|
||||||
MACOSX_DEPLOYMENT_TARGET = 15.0;
|
MACOSX_DEPLOYMENT_TARGET = 10.14;
|
||||||
MARKETING_VERSION = 25.10.21;
|
MARKETING_VERSION = 25.9.17;
|
||||||
OTHER_LDFLAGS = (
|
OTHER_LDFLAGS = (
|
||||||
"-framework",
|
"-framework",
|
||||||
SafariServices,
|
SafariServices,
|
||||||
);
|
);
|
||||||
PRODUCT_BUNDLE_IDENTIFIER = pl.bthlabs.HotPocket.Extension;
|
PRODUCT_BUNDLE_IDENTIFIER = pl.bthlabs.HotPocket.Extension;
|
||||||
PRODUCT_NAME = "HotPocket Extension";
|
PRODUCT_NAME = "HotPocket Extension";
|
||||||
REGISTER_APP_GROUPS = YES;
|
|
||||||
SDKROOT = macosx;
|
SDKROOT = macosx;
|
||||||
SKIP_INSTALL = YES;
|
SKIP_INSTALL = YES;
|
||||||
SWIFT_EMIT_LOC_STRINGS = YES;
|
SWIFT_EMIT_LOC_STRINGS = YES;
|
||||||
|
@ -1015,15 +678,13 @@
|
||||||
ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
|
ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
|
||||||
ASSETCATALOG_COMPILER_GLOBAL_ACCENT_COLOR_NAME = AccentColor;
|
ASSETCATALOG_COMPILER_GLOBAL_ACCENT_COLOR_NAME = AccentColor;
|
||||||
CODE_SIGN_ENTITLEMENTS = "macOS (App)/HotPocket.entitlements";
|
CODE_SIGN_ENTITLEMENTS = "macOS (App)/HotPocket.entitlements";
|
||||||
"CODE_SIGN_IDENTITY[sdk=macosx*]" = "Apple Development";
|
"CODE_SIGN_IDENTITY[sdk=macosx*]" = "-";
|
||||||
CODE_SIGN_STYLE = Automatic;
|
CODE_SIGN_STYLE = Automatic;
|
||||||
CURRENT_PROJECT_VERSION = 2025102101;
|
CURRENT_PROJECT_VERSION = 2025091701;
|
||||||
DEVELOPMENT_TEAM = 648728X64K;
|
DEVELOPMENT_TEAM = 648728X64K;
|
||||||
ENABLE_HARDENED_RUNTIME = YES;
|
ENABLE_HARDENED_RUNTIME = YES;
|
||||||
GENERATE_INFOPLIST_FILE = YES;
|
GENERATE_INFOPLIST_FILE = YES;
|
||||||
INFOPLIST_FILE = "macOS (App)/Info.plist";
|
|
||||||
INFOPLIST_KEY_CFBundleDisplayName = HotPocket;
|
INFOPLIST_KEY_CFBundleDisplayName = HotPocket;
|
||||||
INFOPLIST_KEY_ITSAppUsesNonExemptEncryption = NO;
|
|
||||||
INFOPLIST_KEY_LSApplicationCategoryType = "public.app-category.utilities";
|
INFOPLIST_KEY_LSApplicationCategoryType = "public.app-category.utilities";
|
||||||
INFOPLIST_KEY_NSHumanReadableCopyright = "Copyright © 2025-present BTHLabs";
|
INFOPLIST_KEY_NSHumanReadableCopyright = "Copyright © 2025-present BTHLabs";
|
||||||
INFOPLIST_KEY_NSMainStoryboardFile = Main;
|
INFOPLIST_KEY_NSMainStoryboardFile = Main;
|
||||||
|
@ -1033,7 +694,7 @@
|
||||||
"@executable_path/../Frameworks",
|
"@executable_path/../Frameworks",
|
||||||
);
|
);
|
||||||
MACOSX_DEPLOYMENT_TARGET = 15.0;
|
MACOSX_DEPLOYMENT_TARGET = 15.0;
|
||||||
MARKETING_VERSION = 25.10.21;
|
MARKETING_VERSION = 25.9.17;
|
||||||
OTHER_LDFLAGS = (
|
OTHER_LDFLAGS = (
|
||||||
"-framework",
|
"-framework",
|
||||||
SafariServices,
|
SafariServices,
|
||||||
|
@ -1056,13 +717,11 @@
|
||||||
CODE_SIGN_ENTITLEMENTS = "macOS (App)/HotPocket.entitlements";
|
CODE_SIGN_ENTITLEMENTS = "macOS (App)/HotPocket.entitlements";
|
||||||
"CODE_SIGN_IDENTITY[sdk=macosx*]" = "Apple Development";
|
"CODE_SIGN_IDENTITY[sdk=macosx*]" = "Apple Development";
|
||||||
CODE_SIGN_STYLE = Automatic;
|
CODE_SIGN_STYLE = Automatic;
|
||||||
CURRENT_PROJECT_VERSION = 2025102101;
|
CURRENT_PROJECT_VERSION = 2025091701;
|
||||||
DEVELOPMENT_TEAM = 648728X64K;
|
DEVELOPMENT_TEAM = 648728X64K;
|
||||||
ENABLE_HARDENED_RUNTIME = YES;
|
ENABLE_HARDENED_RUNTIME = YES;
|
||||||
GENERATE_INFOPLIST_FILE = YES;
|
GENERATE_INFOPLIST_FILE = YES;
|
||||||
INFOPLIST_FILE = "macOS (App)/Info.plist";
|
|
||||||
INFOPLIST_KEY_CFBundleDisplayName = HotPocket;
|
INFOPLIST_KEY_CFBundleDisplayName = HotPocket;
|
||||||
INFOPLIST_KEY_ITSAppUsesNonExemptEncryption = NO;
|
|
||||||
INFOPLIST_KEY_LSApplicationCategoryType = "public.app-category.utilities";
|
INFOPLIST_KEY_LSApplicationCategoryType = "public.app-category.utilities";
|
||||||
INFOPLIST_KEY_NSHumanReadableCopyright = "Copyright © 2025-present BTHLabs";
|
INFOPLIST_KEY_NSHumanReadableCopyright = "Copyright © 2025-present BTHLabs";
|
||||||
INFOPLIST_KEY_NSMainStoryboardFile = Main;
|
INFOPLIST_KEY_NSMainStoryboardFile = Main;
|
||||||
|
@ -1072,7 +731,7 @@
|
||||||
"@executable_path/../Frameworks",
|
"@executable_path/../Frameworks",
|
||||||
);
|
);
|
||||||
MACOSX_DEPLOYMENT_TARGET = 15.0;
|
MACOSX_DEPLOYMENT_TARGET = 15.0;
|
||||||
MARKETING_VERSION = 25.10.21;
|
MARKETING_VERSION = 25.9.17;
|
||||||
OTHER_LDFLAGS = (
|
OTHER_LDFLAGS = (
|
||||||
"-framework",
|
"-framework",
|
||||||
SafariServices,
|
SafariServices,
|
||||||
|
@ -1200,78 +859,9 @@
|
||||||
};
|
};
|
||||||
name = Release;
|
name = Release;
|
||||||
};
|
};
|
||||||
4CBCEA5E2E81CB9500722009 /* Debug */ = {
|
|
||||||
isa = XCBuildConfiguration;
|
|
||||||
buildSettings = {
|
|
||||||
CODE_SIGN_ENTITLEMENTS = "macOS (Share Extension)/macOS (Share Extension).entitlements";
|
|
||||||
CODE_SIGN_STYLE = Automatic;
|
|
||||||
COMBINE_HIDPI_IMAGES = YES;
|
|
||||||
CURRENT_PROJECT_VERSION = 2025102101;
|
|
||||||
DEVELOPMENT_TEAM = 648728X64K;
|
|
||||||
ENABLE_HARDENED_RUNTIME = YES;
|
|
||||||
GENERATE_INFOPLIST_FILE = YES;
|
|
||||||
INFOPLIST_FILE = "macOS (Share Extension)/Info.plist";
|
|
||||||
INFOPLIST_KEY_CFBundleDisplayName = "Save to HotPocket";
|
|
||||||
INFOPLIST_KEY_ITSAppUsesNonExemptEncryption = NO;
|
|
||||||
INFOPLIST_KEY_NSHumanReadableCopyright = "Copyright © 2025-present BTHLabs";
|
|
||||||
LD_RUNPATH_SEARCH_PATHS = (
|
|
||||||
"$(inherited)",
|
|
||||||
"@executable_path/../Frameworks",
|
|
||||||
"@executable_path/../../../../Frameworks",
|
|
||||||
);
|
|
||||||
MACOSX_DEPLOYMENT_TARGET = 15.0;
|
|
||||||
MARKETING_VERSION = 25.10.21;
|
|
||||||
PRODUCT_BUNDLE_IDENTIFIER = pl.bthlabs.HotPocket.ShareExtension;
|
|
||||||
PRODUCT_NAME = "Save to HotPocket";
|
|
||||||
REGISTER_APP_GROUPS = YES;
|
|
||||||
SDKROOT = macosx;
|
|
||||||
SKIP_INSTALL = YES;
|
|
||||||
SWIFT_EMIT_LOC_STRINGS = YES;
|
|
||||||
};
|
|
||||||
name = Debug;
|
|
||||||
};
|
|
||||||
4CBCEA5F2E81CB9500722009 /* Release */ = {
|
|
||||||
isa = XCBuildConfiguration;
|
|
||||||
buildSettings = {
|
|
||||||
CODE_SIGN_ENTITLEMENTS = "macOS (Share Extension)/macOS (Share Extension).entitlements";
|
|
||||||
CODE_SIGN_STYLE = Automatic;
|
|
||||||
COMBINE_HIDPI_IMAGES = YES;
|
|
||||||
CURRENT_PROJECT_VERSION = 2025102101;
|
|
||||||
DEVELOPMENT_TEAM = 648728X64K;
|
|
||||||
ENABLE_HARDENED_RUNTIME = YES;
|
|
||||||
GENERATE_INFOPLIST_FILE = YES;
|
|
||||||
INFOPLIST_FILE = "macOS (Share Extension)/Info.plist";
|
|
||||||
INFOPLIST_KEY_CFBundleDisplayName = "Save to HotPocket";
|
|
||||||
INFOPLIST_KEY_ITSAppUsesNonExemptEncryption = NO;
|
|
||||||
INFOPLIST_KEY_NSHumanReadableCopyright = "Copyright © 2025-present BTHLabs";
|
|
||||||
LD_RUNPATH_SEARCH_PATHS = (
|
|
||||||
"$(inherited)",
|
|
||||||
"@executable_path/../Frameworks",
|
|
||||||
"@executable_path/../../../../Frameworks",
|
|
||||||
);
|
|
||||||
MACOSX_DEPLOYMENT_TARGET = 15.0;
|
|
||||||
MARKETING_VERSION = 25.10.21;
|
|
||||||
PRODUCT_BUNDLE_IDENTIFIER = pl.bthlabs.HotPocket.ShareExtension;
|
|
||||||
PRODUCT_NAME = "Save to HotPocket";
|
|
||||||
REGISTER_APP_GROUPS = YES;
|
|
||||||
SDKROOT = macosx;
|
|
||||||
SKIP_INSTALL = YES;
|
|
||||||
SWIFT_EMIT_LOC_STRINGS = YES;
|
|
||||||
};
|
|
||||||
name = Release;
|
|
||||||
};
|
|
||||||
/* End XCBuildConfiguration section */
|
/* End XCBuildConfiguration section */
|
||||||
|
|
||||||
/* Begin XCConfigurationList section */
|
/* Begin XCConfigurationList section */
|
||||||
4C2F0C6A2E851BBD0033F5C2 /* Build configuration list for PBXNativeTarget "iOS (Share Extension)" */ = {
|
|
||||||
isa = XCConfigurationList;
|
|
||||||
buildConfigurations = (
|
|
||||||
4C2F0C6B2E851BBD0033F5C2 /* Debug */,
|
|
||||||
4C2F0C6C2E851BBD0033F5C2 /* Release */,
|
|
||||||
);
|
|
||||||
defaultConfigurationIsVisible = 0;
|
|
||||||
defaultConfigurationName = Release;
|
|
||||||
};
|
|
||||||
4CABCA952E56F0C800D8A354 /* Build configuration list for PBXProject "HotPocket" */ = {
|
4CABCA952E56F0C800D8A354 /* Build configuration list for PBXProject "HotPocket" */ = {
|
||||||
isa = XCConfigurationList;
|
isa = XCConfigurationList;
|
||||||
buildConfigurations = (
|
buildConfigurations = (
|
||||||
|
@ -1317,15 +907,6 @@
|
||||||
defaultConfigurationIsVisible = 0;
|
defaultConfigurationIsVisible = 0;
|
||||||
defaultConfigurationName = Release;
|
defaultConfigurationName = Release;
|
||||||
};
|
};
|
||||||
4CBCEA602E81CB9500722009 /* Build configuration list for PBXNativeTarget "macOS (Share Extension)" */ = {
|
|
||||||
isa = XCConfigurationList;
|
|
||||||
buildConfigurations = (
|
|
||||||
4CBCEA5E2E81CB9500722009 /* Debug */,
|
|
||||||
4CBCEA5F2E81CB9500722009 /* Release */,
|
|
||||||
);
|
|
||||||
defaultConfigurationIsVisible = 0;
|
|
||||||
defaultConfigurationName = Release;
|
|
||||||
};
|
|
||||||
/* End XCConfigurationList section */
|
/* End XCConfigurationList section */
|
||||||
};
|
};
|
||||||
rootObject = 4CABCA922E56F0C800D8A354 /* Project object */;
|
rootObject = 4CABCA922E56F0C800D8A354 /* Project object */;
|
||||||
|
|
|
@ -1,78 +0,0 @@
|
||||||
<?xml version="1.0" encoding="UTF-8"?>
|
|
||||||
<Scheme
|
|
||||||
LastUpgradeVersion = "2600"
|
|
||||||
version = "1.7">
|
|
||||||
<BuildAction
|
|
||||||
parallelizeBuildables = "YES"
|
|
||||||
buildImplicitDependencies = "YES"
|
|
||||||
buildArchitectures = "Automatic">
|
|
||||||
<BuildActionEntries>
|
|
||||||
<BuildActionEntry
|
|
||||||
buildForTesting = "YES"
|
|
||||||
buildForRunning = "YES"
|
|
||||||
buildForProfiling = "YES"
|
|
||||||
buildForArchiving = "YES"
|
|
||||||
buildForAnalyzing = "YES">
|
|
||||||
<BuildableReference
|
|
||||||
BuildableIdentifier = "primary"
|
|
||||||
BlueprintIdentifier = "4CABCAAF2E56F0C900D8A354"
|
|
||||||
BuildableName = "HotPocket.app"
|
|
||||||
BlueprintName = "HotPocket (iOS)"
|
|
||||||
ReferencedContainer = "container:HotPocket.xcodeproj">
|
|
||||||
</BuildableReference>
|
|
||||||
</BuildActionEntry>
|
|
||||||
</BuildActionEntries>
|
|
||||||
</BuildAction>
|
|
||||||
<TestAction
|
|
||||||
buildConfiguration = "Debug"
|
|
||||||
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
|
|
||||||
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
|
|
||||||
shouldUseLaunchSchemeArgsEnv = "YES"
|
|
||||||
shouldAutocreateTestPlan = "YES">
|
|
||||||
</TestAction>
|
|
||||||
<LaunchAction
|
|
||||||
buildConfiguration = "Debug"
|
|
||||||
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
|
|
||||||
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
|
|
||||||
launchStyle = "0"
|
|
||||||
useCustomWorkingDirectory = "NO"
|
|
||||||
ignoresPersistentStateOnLaunch = "NO"
|
|
||||||
debugDocumentVersioning = "YES"
|
|
||||||
debugServiceExtension = "internal"
|
|
||||||
allowLocationSimulation = "YES">
|
|
||||||
<BuildableProductRunnable
|
|
||||||
runnableDebuggingMode = "0">
|
|
||||||
<BuildableReference
|
|
||||||
BuildableIdentifier = "primary"
|
|
||||||
BlueprintIdentifier = "4CABCAAF2E56F0C900D8A354"
|
|
||||||
BuildableName = "HotPocket.app"
|
|
||||||
BlueprintName = "HotPocket (iOS)"
|
|
||||||
ReferencedContainer = "container:HotPocket.xcodeproj">
|
|
||||||
</BuildableReference>
|
|
||||||
</BuildableProductRunnable>
|
|
||||||
</LaunchAction>
|
|
||||||
<ProfileAction
|
|
||||||
buildConfiguration = "Release"
|
|
||||||
shouldUseLaunchSchemeArgsEnv = "YES"
|
|
||||||
savedToolIdentifier = ""
|
|
||||||
useCustomWorkingDirectory = "NO"
|
|
||||||
debugDocumentVersioning = "YES">
|
|
||||||
<BuildableProductRunnable
|
|
||||||
runnableDebuggingMode = "0">
|
|
||||||
<BuildableReference
|
|
||||||
BuildableIdentifier = "primary"
|
|
||||||
BlueprintIdentifier = "4CABCAAF2E56F0C900D8A354"
|
|
||||||
BuildableName = "HotPocket.app"
|
|
||||||
BlueprintName = "HotPocket (iOS)"
|
|
||||||
ReferencedContainer = "container:HotPocket.xcodeproj">
|
|
||||||
</BuildableReference>
|
|
||||||
</BuildableProductRunnable>
|
|
||||||
</ProfileAction>
|
|
||||||
<AnalyzeAction
|
|
||||||
buildConfiguration = "Debug">
|
|
||||||
</AnalyzeAction>
|
|
||||||
<ArchiveAction
|
|
||||||
buildConfiguration = "Release"
|
|
||||||
revealArchiveInOrganizer = "YES">
|
|
||||||
</ArchiveAction>
|
|
||||||
</Scheme>
|
|
|
@ -1,78 +0,0 @@
|
||||||
<?xml version="1.0" encoding="UTF-8"?>
|
|
||||||
<Scheme
|
|
||||||
LastUpgradeVersion = "2600"
|
|
||||||
version = "1.7">
|
|
||||||
<BuildAction
|
|
||||||
parallelizeBuildables = "YES"
|
|
||||||
buildImplicitDependencies = "YES"
|
|
||||||
buildArchitectures = "Automatic">
|
|
||||||
<BuildActionEntries>
|
|
||||||
<BuildActionEntry
|
|
||||||
buildForTesting = "YES"
|
|
||||||
buildForRunning = "YES"
|
|
||||||
buildForProfiling = "YES"
|
|
||||||
buildForArchiving = "YES"
|
|
||||||
buildForAnalyzing = "YES">
|
|
||||||
<BuildableReference
|
|
||||||
BuildableIdentifier = "primary"
|
|
||||||
BlueprintIdentifier = "4CABCAC52E56F0C900D8A354"
|
|
||||||
BuildableName = "HotPocket.app"
|
|
||||||
BlueprintName = "HotPocket (macOS)"
|
|
||||||
ReferencedContainer = "container:HotPocket.xcodeproj">
|
|
||||||
</BuildableReference>
|
|
||||||
</BuildActionEntry>
|
|
||||||
</BuildActionEntries>
|
|
||||||
</BuildAction>
|
|
||||||
<TestAction
|
|
||||||
buildConfiguration = "Debug"
|
|
||||||
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
|
|
||||||
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
|
|
||||||
shouldUseLaunchSchemeArgsEnv = "YES"
|
|
||||||
shouldAutocreateTestPlan = "YES">
|
|
||||||
</TestAction>
|
|
||||||
<LaunchAction
|
|
||||||
buildConfiguration = "Debug"
|
|
||||||
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
|
|
||||||
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
|
|
||||||
launchStyle = "0"
|
|
||||||
useCustomWorkingDirectory = "NO"
|
|
||||||
ignoresPersistentStateOnLaunch = "NO"
|
|
||||||
debugDocumentVersioning = "YES"
|
|
||||||
debugServiceExtension = "internal"
|
|
||||||
allowLocationSimulation = "YES">
|
|
||||||
<BuildableProductRunnable
|
|
||||||
runnableDebuggingMode = "0">
|
|
||||||
<BuildableReference
|
|
||||||
BuildableIdentifier = "primary"
|
|
||||||
BlueprintIdentifier = "4CABCAC52E56F0C900D8A354"
|
|
||||||
BuildableName = "HotPocket.app"
|
|
||||||
BlueprintName = "HotPocket (macOS)"
|
|
||||||
ReferencedContainer = "container:HotPocket.xcodeproj">
|
|
||||||
</BuildableReference>
|
|
||||||
</BuildableProductRunnable>
|
|
||||||
</LaunchAction>
|
|
||||||
<ProfileAction
|
|
||||||
buildConfiguration = "Release"
|
|
||||||
shouldUseLaunchSchemeArgsEnv = "YES"
|
|
||||||
savedToolIdentifier = ""
|
|
||||||
useCustomWorkingDirectory = "NO"
|
|
||||||
debugDocumentVersioning = "YES">
|
|
||||||
<BuildableProductRunnable
|
|
||||||
runnableDebuggingMode = "0">
|
|
||||||
<BuildableReference
|
|
||||||
BuildableIdentifier = "primary"
|
|
||||||
BlueprintIdentifier = "4CABCAC52E56F0C900D8A354"
|
|
||||||
BuildableName = "HotPocket.app"
|
|
||||||
BlueprintName = "HotPocket (macOS)"
|
|
||||||
ReferencedContainer = "container:HotPocket.xcodeproj">
|
|
||||||
</BuildableReference>
|
|
||||||
</BuildableProductRunnable>
|
|
||||||
</ProfileAction>
|
|
||||||
<AnalyzeAction
|
|
||||||
buildConfiguration = "Debug">
|
|
||||||
</AnalyzeAction>
|
|
||||||
<ArchiveAction
|
|
||||||
buildConfiguration = "Release"
|
|
||||||
revealArchiveInOrganizer = "YES">
|
|
||||||
</ArchiveAction>
|
|
||||||
</Scheme>
|
|
|
@ -1,97 +0,0 @@
|
||||||
<?xml version="1.0" encoding="UTF-8"?>
|
|
||||||
<Scheme
|
|
||||||
LastUpgradeVersion = "2600"
|
|
||||||
wasCreatedForAppExtension = "YES"
|
|
||||||
version = "2.0">
|
|
||||||
<BuildAction
|
|
||||||
parallelizeBuildables = "YES"
|
|
||||||
buildImplicitDependencies = "YES"
|
|
||||||
buildArchitectures = "Automatic">
|
|
||||||
<BuildActionEntries>
|
|
||||||
<BuildActionEntry
|
|
||||||
buildForTesting = "YES"
|
|
||||||
buildForRunning = "YES"
|
|
||||||
buildForProfiling = "YES"
|
|
||||||
buildForArchiving = "YES"
|
|
||||||
buildForAnalyzing = "YES">
|
|
||||||
<BuildableReference
|
|
||||||
BuildableIdentifier = "primary"
|
|
||||||
BlueprintIdentifier = "4CABCAD42E56F0C900D8A354"
|
|
||||||
BuildableName = "HotPocket Extension.appex"
|
|
||||||
BlueprintName = "HotPocket Extension (iOS)"
|
|
||||||
ReferencedContainer = "container:HotPocket.xcodeproj">
|
|
||||||
</BuildableReference>
|
|
||||||
</BuildActionEntry>
|
|
||||||
<BuildActionEntry
|
|
||||||
buildForTesting = "YES"
|
|
||||||
buildForRunning = "YES"
|
|
||||||
buildForProfiling = "YES"
|
|
||||||
buildForArchiving = "YES"
|
|
||||||
buildForAnalyzing = "YES">
|
|
||||||
<BuildableReference
|
|
||||||
BuildableIdentifier = "primary"
|
|
||||||
BlueprintIdentifier = "4CABCAAF2E56F0C900D8A354"
|
|
||||||
BuildableName = "HotPocket.app"
|
|
||||||
BlueprintName = "HotPocket (iOS)"
|
|
||||||
ReferencedContainer = "container:HotPocket.xcodeproj">
|
|
||||||
</BuildableReference>
|
|
||||||
</BuildActionEntry>
|
|
||||||
</BuildActionEntries>
|
|
||||||
</BuildAction>
|
|
||||||
<TestAction
|
|
||||||
buildConfiguration = "Debug"
|
|
||||||
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
|
|
||||||
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
|
|
||||||
shouldUseLaunchSchemeArgsEnv = "YES"
|
|
||||||
shouldAutocreateTestPlan = "YES">
|
|
||||||
</TestAction>
|
|
||||||
<LaunchAction
|
|
||||||
buildConfiguration = "Debug"
|
|
||||||
selectedDebuggerIdentifier = ""
|
|
||||||
selectedLauncherIdentifier = "Xcode.IDEFoundation.Launcher.PosixSpawn"
|
|
||||||
launchStyle = "0"
|
|
||||||
askForAppToLaunch = "Yes"
|
|
||||||
useCustomWorkingDirectory = "NO"
|
|
||||||
ignoresPersistentStateOnLaunch = "NO"
|
|
||||||
debugDocumentVersioning = "YES"
|
|
||||||
debugServiceExtension = "internal"
|
|
||||||
allowLocationSimulation = "YES"
|
|
||||||
launchAutomaticallySubstyle = "2">
|
|
||||||
<BuildableProductRunnable
|
|
||||||
runnableDebuggingMode = "0">
|
|
||||||
<BuildableReference
|
|
||||||
BuildableIdentifier = "primary"
|
|
||||||
BlueprintIdentifier = "4CABCAAF2E56F0C900D8A354"
|
|
||||||
BuildableName = "HotPocket.app"
|
|
||||||
BlueprintName = "HotPocket (iOS)"
|
|
||||||
ReferencedContainer = "container:HotPocket.xcodeproj">
|
|
||||||
</BuildableReference>
|
|
||||||
</BuildableProductRunnable>
|
|
||||||
</LaunchAction>
|
|
||||||
<ProfileAction
|
|
||||||
buildConfiguration = "Release"
|
|
||||||
shouldUseLaunchSchemeArgsEnv = "YES"
|
|
||||||
savedToolIdentifier = ""
|
|
||||||
useCustomWorkingDirectory = "NO"
|
|
||||||
debugDocumentVersioning = "YES"
|
|
||||||
askForAppToLaunch = "Yes"
|
|
||||||
launchAutomaticallySubstyle = "2">
|
|
||||||
<BuildableProductRunnable
|
|
||||||
runnableDebuggingMode = "0">
|
|
||||||
<BuildableReference
|
|
||||||
BuildableIdentifier = "primary"
|
|
||||||
BlueprintIdentifier = "4CABCAAF2E56F0C900D8A354"
|
|
||||||
BuildableName = "HotPocket.app"
|
|
||||||
BlueprintName = "HotPocket (iOS)"
|
|
||||||
ReferencedContainer = "container:HotPocket.xcodeproj">
|
|
||||||
</BuildableReference>
|
|
||||||
</BuildableProductRunnable>
|
|
||||||
</ProfileAction>
|
|
||||||
<AnalyzeAction
|
|
||||||
buildConfiguration = "Debug">
|
|
||||||
</AnalyzeAction>
|
|
||||||
<ArchiveAction
|
|
||||||
buildConfiguration = "Release"
|
|
||||||
revealArchiveInOrganizer = "YES">
|
|
||||||
</ArchiveAction>
|
|
||||||
</Scheme>
|
|
|
@ -1,97 +0,0 @@
|
||||||
<?xml version="1.0" encoding="UTF-8"?>
|
|
||||||
<Scheme
|
|
||||||
LastUpgradeVersion = "2600"
|
|
||||||
wasCreatedForAppExtension = "YES"
|
|
||||||
version = "2.0">
|
|
||||||
<BuildAction
|
|
||||||
parallelizeBuildables = "YES"
|
|
||||||
buildImplicitDependencies = "YES"
|
|
||||||
buildArchitectures = "Automatic">
|
|
||||||
<BuildActionEntries>
|
|
||||||
<BuildActionEntry
|
|
||||||
buildForTesting = "YES"
|
|
||||||
buildForRunning = "YES"
|
|
||||||
buildForProfiling = "YES"
|
|
||||||
buildForArchiving = "YES"
|
|
||||||
buildForAnalyzing = "YES">
|
|
||||||
<BuildableReference
|
|
||||||
BuildableIdentifier = "primary"
|
|
||||||
BlueprintIdentifier = "4CABCADE2E56F0C900D8A354"
|
|
||||||
BuildableName = "HotPocket Extension.appex"
|
|
||||||
BlueprintName = "HotPocket Extension (macOS)"
|
|
||||||
ReferencedContainer = "container:HotPocket.xcodeproj">
|
|
||||||
</BuildableReference>
|
|
||||||
</BuildActionEntry>
|
|
||||||
<BuildActionEntry
|
|
||||||
buildForTesting = "YES"
|
|
||||||
buildForRunning = "YES"
|
|
||||||
buildForProfiling = "YES"
|
|
||||||
buildForArchiving = "YES"
|
|
||||||
buildForAnalyzing = "YES">
|
|
||||||
<BuildableReference
|
|
||||||
BuildableIdentifier = "primary"
|
|
||||||
BlueprintIdentifier = "4CABCAC52E56F0C900D8A354"
|
|
||||||
BuildableName = "HotPocket.app"
|
|
||||||
BlueprintName = "HotPocket (macOS)"
|
|
||||||
ReferencedContainer = "container:HotPocket.xcodeproj">
|
|
||||||
</BuildableReference>
|
|
||||||
</BuildActionEntry>
|
|
||||||
</BuildActionEntries>
|
|
||||||
</BuildAction>
|
|
||||||
<TestAction
|
|
||||||
buildConfiguration = "Debug"
|
|
||||||
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
|
|
||||||
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
|
|
||||||
shouldUseLaunchSchemeArgsEnv = "YES"
|
|
||||||
shouldAutocreateTestPlan = "YES">
|
|
||||||
</TestAction>
|
|
||||||
<LaunchAction
|
|
||||||
buildConfiguration = "Debug"
|
|
||||||
selectedDebuggerIdentifier = ""
|
|
||||||
selectedLauncherIdentifier = "Xcode.IDEFoundation.Launcher.PosixSpawn"
|
|
||||||
launchStyle = "0"
|
|
||||||
askForAppToLaunch = "Yes"
|
|
||||||
useCustomWorkingDirectory = "NO"
|
|
||||||
ignoresPersistentStateOnLaunch = "NO"
|
|
||||||
debugDocumentVersioning = "YES"
|
|
||||||
debugServiceExtension = "internal"
|
|
||||||
allowLocationSimulation = "YES"
|
|
||||||
launchAutomaticallySubstyle = "2">
|
|
||||||
<BuildableProductRunnable
|
|
||||||
runnableDebuggingMode = "0">
|
|
||||||
<BuildableReference
|
|
||||||
BuildableIdentifier = "primary"
|
|
||||||
BlueprintIdentifier = "4CABCAC52E56F0C900D8A354"
|
|
||||||
BuildableName = "HotPocket.app"
|
|
||||||
BlueprintName = "HotPocket (macOS)"
|
|
||||||
ReferencedContainer = "container:HotPocket.xcodeproj">
|
|
||||||
</BuildableReference>
|
|
||||||
</BuildableProductRunnable>
|
|
||||||
</LaunchAction>
|
|
||||||
<ProfileAction
|
|
||||||
buildConfiguration = "Release"
|
|
||||||
shouldUseLaunchSchemeArgsEnv = "YES"
|
|
||||||
savedToolIdentifier = ""
|
|
||||||
useCustomWorkingDirectory = "NO"
|
|
||||||
debugDocumentVersioning = "YES"
|
|
||||||
askForAppToLaunch = "Yes"
|
|
||||||
launchAutomaticallySubstyle = "2">
|
|
||||||
<BuildableProductRunnable
|
|
||||||
runnableDebuggingMode = "0">
|
|
||||||
<BuildableReference
|
|
||||||
BuildableIdentifier = "primary"
|
|
||||||
BlueprintIdentifier = "4CABCAC52E56F0C900D8A354"
|
|
||||||
BuildableName = "HotPocket.app"
|
|
||||||
BlueprintName = "HotPocket (macOS)"
|
|
||||||
ReferencedContainer = "container:HotPocket.xcodeproj">
|
|
||||||
</BuildableReference>
|
|
||||||
</BuildableProductRunnable>
|
|
||||||
</ProfileAction>
|
|
||||||
<AnalyzeAction
|
|
||||||
buildConfiguration = "Debug">
|
|
||||||
</AnalyzeAction>
|
|
||||||
<ArchiveAction
|
|
||||||
buildConfiguration = "Release"
|
|
||||||
revealArchiveInOrganizer = "YES">
|
|
||||||
</ArchiveAction>
|
|
||||||
</Scheme>
|
|
|
@ -1,97 +0,0 @@
|
||||||
<?xml version="1.0" encoding="UTF-8"?>
|
|
||||||
<Scheme
|
|
||||||
LastUpgradeVersion = "2600"
|
|
||||||
wasCreatedForAppExtension = "YES"
|
|
||||||
version = "2.0">
|
|
||||||
<BuildAction
|
|
||||||
parallelizeBuildables = "YES"
|
|
||||||
buildImplicitDependencies = "YES"
|
|
||||||
buildArchitectures = "Automatic">
|
|
||||||
<BuildActionEntries>
|
|
||||||
<BuildActionEntry
|
|
||||||
buildForTesting = "YES"
|
|
||||||
buildForRunning = "YES"
|
|
||||||
buildForProfiling = "YES"
|
|
||||||
buildForArchiving = "YES"
|
|
||||||
buildForAnalyzing = "YES">
|
|
||||||
<BuildableReference
|
|
||||||
BuildableIdentifier = "primary"
|
|
||||||
BlueprintIdentifier = "4CBCEA4E2E81CB9500722009"
|
|
||||||
BuildableName = "Save to HotPocket.appex"
|
|
||||||
BlueprintName = "macOS (Share Extension)"
|
|
||||||
ReferencedContainer = "container:HotPocket.xcodeproj">
|
|
||||||
</BuildableReference>
|
|
||||||
</BuildActionEntry>
|
|
||||||
<BuildActionEntry
|
|
||||||
buildForTesting = "YES"
|
|
||||||
buildForRunning = "YES"
|
|
||||||
buildForProfiling = "YES"
|
|
||||||
buildForArchiving = "YES"
|
|
||||||
buildForAnalyzing = "YES">
|
|
||||||
<BuildableReference
|
|
||||||
BuildableIdentifier = "primary"
|
|
||||||
BlueprintIdentifier = "4CABCAC52E56F0C900D8A354"
|
|
||||||
BuildableName = "HotPocket.app"
|
|
||||||
BlueprintName = "HotPocket (macOS)"
|
|
||||||
ReferencedContainer = "container:HotPocket.xcodeproj">
|
|
||||||
</BuildableReference>
|
|
||||||
</BuildActionEntry>
|
|
||||||
</BuildActionEntries>
|
|
||||||
</BuildAction>
|
|
||||||
<TestAction
|
|
||||||
buildConfiguration = "Debug"
|
|
||||||
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
|
|
||||||
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
|
|
||||||
shouldUseLaunchSchemeArgsEnv = "YES"
|
|
||||||
shouldAutocreateTestPlan = "YES">
|
|
||||||
</TestAction>
|
|
||||||
<LaunchAction
|
|
||||||
buildConfiguration = "Debug"
|
|
||||||
selectedDebuggerIdentifier = ""
|
|
||||||
selectedLauncherIdentifier = "Xcode.IDEFoundation.Launcher.PosixSpawn"
|
|
||||||
launchStyle = "0"
|
|
||||||
askForAppToLaunch = "Yes"
|
|
||||||
useCustomWorkingDirectory = "NO"
|
|
||||||
ignoresPersistentStateOnLaunch = "NO"
|
|
||||||
debugDocumentVersioning = "YES"
|
|
||||||
debugServiceExtension = "internal"
|
|
||||||
allowLocationSimulation = "YES"
|
|
||||||
launchAutomaticallySubstyle = "2">
|
|
||||||
<BuildableProductRunnable
|
|
||||||
runnableDebuggingMode = "0">
|
|
||||||
<BuildableReference
|
|
||||||
BuildableIdentifier = "primary"
|
|
||||||
BlueprintIdentifier = "4CABCAC52E56F0C900D8A354"
|
|
||||||
BuildableName = "HotPocket.app"
|
|
||||||
BlueprintName = "HotPocket (macOS)"
|
|
||||||
ReferencedContainer = "container:HotPocket.xcodeproj">
|
|
||||||
</BuildableReference>
|
|
||||||
</BuildableProductRunnable>
|
|
||||||
</LaunchAction>
|
|
||||||
<ProfileAction
|
|
||||||
buildConfiguration = "Release"
|
|
||||||
shouldUseLaunchSchemeArgsEnv = "YES"
|
|
||||||
savedToolIdentifier = ""
|
|
||||||
useCustomWorkingDirectory = "NO"
|
|
||||||
debugDocumentVersioning = "YES"
|
|
||||||
askForAppToLaunch = "Yes"
|
|
||||||
launchAutomaticallySubstyle = "2">
|
|
||||||
<BuildableProductRunnable
|
|
||||||
runnableDebuggingMode = "0">
|
|
||||||
<BuildableReference
|
|
||||||
BuildableIdentifier = "primary"
|
|
||||||
BlueprintIdentifier = "4CABCAC52E56F0C900D8A354"
|
|
||||||
BuildableName = "HotPocket.app"
|
|
||||||
BlueprintName = "HotPocket (macOS)"
|
|
||||||
ReferencedContainer = "container:HotPocket.xcodeproj">
|
|
||||||
</BuildableReference>
|
|
||||||
</BuildableProductRunnable>
|
|
||||||
</ProfileAction>
|
|
||||||
<AnalyzeAction
|
|
||||||
buildConfiguration = "Debug">
|
|
||||||
</AnalyzeAction>
|
|
||||||
<ArchiveAction
|
|
||||||
buildConfiguration = "Release"
|
|
||||||
revealArchiveInOrganizer = "YES">
|
|
||||||
</ArchiveAction>
|
|
||||||
</Scheme>
|
|
|
@ -1,7 +1,7 @@
|
||||||
{
|
{
|
||||||
"images" : [
|
"images" : [
|
||||||
{
|
{
|
||||||
"filename" : "icon-ios-light.png",
|
"filename" : "icon-1024.png",
|
||||||
"idiom" : "universal",
|
"idiom" : "universal",
|
||||||
"platform" : "ios",
|
"platform" : "ios",
|
||||||
"size" : "1024x1024"
|
"size" : "1024x1024"
|
||||||
|
@ -13,7 +13,7 @@
|
||||||
"value" : "dark"
|
"value" : "dark"
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
"filename" : "icon-ios-dark.png",
|
"filename" : "icon-1024 1.png",
|
||||||
"idiom" : "universal",
|
"idiom" : "universal",
|
||||||
"platform" : "ios",
|
"platform" : "ios",
|
||||||
"size" : "1024x1024"
|
"size" : "1024x1024"
|
||||||
|
@ -25,31 +25,31 @@
|
||||||
"value" : "tinted"
|
"value" : "tinted"
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
"filename" : "icon-ios-tinted.png",
|
"filename" : "icon-1024 2.png",
|
||||||
"idiom" : "universal",
|
"idiom" : "universal",
|
||||||
"platform" : "ios",
|
"platform" : "ios",
|
||||||
"size" : "1024x1024"
|
"size" : "1024x1024"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"filename" : "icon-mac-16.png",
|
"filename" : "icon-16.png",
|
||||||
"idiom" : "mac",
|
"idiom" : "mac",
|
||||||
"scale" : "1x",
|
"scale" : "1x",
|
||||||
"size" : "16x16"
|
"size" : "16x16"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"filename" : "icon-mac-32.png",
|
"filename" : "icon-32.png",
|
||||||
"idiom" : "mac",
|
"idiom" : "mac",
|
||||||
"scale" : "2x",
|
"scale" : "2x",
|
||||||
"size" : "16x16"
|
"size" : "16x16"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"filename" : "icon-mac-32 1.png",
|
"filename" : "icon-32 1.png",
|
||||||
"idiom" : "mac",
|
"idiom" : "mac",
|
||||||
"scale" : "1x",
|
"scale" : "1x",
|
||||||
"size" : "32x32"
|
"size" : "32x32"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"filename" : "icon-mac-64.png",
|
"filename" : "icon-64.png",
|
||||||
"idiom" : "mac",
|
"idiom" : "mac",
|
||||||
"scale" : "2x",
|
"scale" : "2x",
|
||||||
"size" : "32x32"
|
"size" : "32x32"
|
||||||
|
|
After Width: | Height: | Size: 115 KiB |
After Width: | Height: | Size: 115 KiB |
After Width: | Height: | Size: 115 KiB |
After Width: | Height: | Size: 874 B |
After Width: | Height: | Size: 2.1 KiB |
After Width: | Height: | Size: 2.1 KiB |
After Width: | Height: | Size: 5.7 KiB |
Before Width: | Height: | Size: 285 KiB |
Before Width: | Height: | Size: 323 KiB |
Before Width: | Height: | Size: 70 KiB |
Before Width: | Height: | Size: 116 KiB After Width: | Height: | Size: 117 KiB |
Before Width: | Height: | Size: 828 B |
Before Width: | Height: | Size: 2.1 KiB |
Before Width: | Height: | Size: 2.1 KiB |
Before Width: | Height: | Size: 5.4 KiB |
|
@ -1,20 +0,0 @@
|
||||||
{
|
|
||||||
"colors" : [
|
|
||||||
{
|
|
||||||
"color" : {
|
|
||||||
"color-space" : "srgb",
|
|
||||||
"components" : {
|
|
||||||
"alpha" : "1.000",
|
|
||||||
"blue" : "0x76",
|
|
||||||
"green" : "0x64",
|
|
||||||
"red" : "0xEE"
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"idiom" : "universal"
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"info" : {
|
|
||||||
"author" : "xcode",
|
|
||||||
"version" : 1
|
|
||||||
}
|
|
||||||
}
|
|
Before Width: | Height: | Size: 13 KiB After Width: | Height: | Size: 14 KiB |
Before Width: | Height: | Size: 34 KiB After Width: | Height: | Size: 35 KiB |
Before Width: | Height: | Size: 58 KiB After Width: | Height: | Size: 63 KiB |
|
@ -1,20 +0,0 @@
|
||||||
{
|
|
||||||
"colors" : [
|
|
||||||
{
|
|
||||||
"color" : {
|
|
||||||
"color-space" : "srgb",
|
|
||||||
"components" : {
|
|
||||||
"alpha" : "1.000",
|
|
||||||
"blue" : "0x67",
|
|
||||||
"green" : "0xA7",
|
|
||||||
"red" : "0x0E"
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"idiom" : "universal"
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"info" : {
|
|
||||||
"author" : "xcode",
|
|
||||||
"version" : 1
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -1,20 +0,0 @@
|
||||||
{
|
|
||||||
"colors" : [
|
|
||||||
{
|
|
||||||
"color" : {
|
|
||||||
"color-space" : "srgb",
|
|
||||||
"components" : {
|
|
||||||
"alpha" : "1.000",
|
|
||||||
"blue" : "0x2E",
|
|
||||||
"green" : "0x96",
|
|
||||||
"red" : "0xF1"
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"idiom" : "universal"
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"info" : {
|
|
||||||
"author" : "xcode",
|
|
||||||
"version" : 1
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -1,32 +0,0 @@
|
||||||
//
|
|
||||||
// HPAPI.h
|
|
||||||
// HotPocket
|
|
||||||
//
|
|
||||||
// Created by Tomek Wójcik on 23/09/2025.
|
|
||||||
//
|
|
||||||
|
|
||||||
#import <Foundation/Foundation.h>
|
|
||||||
|
|
||||||
#import "HPRPCClient.h"
|
|
||||||
|
|
||||||
NS_ASSUME_NONNULL_BEGIN
|
|
||||||
|
|
||||||
typedef void (^HPAPICheckAuthCompletionHandler)(BOOL authValid, NSError * _Nullable error, NSString * _Nullable callId);
|
|
||||||
|
|
||||||
@interface HPAPI : NSObject
|
|
||||||
|
|
||||||
@property (nullable) HPRPCClient *rpcClient;
|
|
||||||
@property NSMutableSet *callIds;
|
|
||||||
|
|
||||||
-(id)initWithRPCClientDelegate:(id<HPRPCClientDelegate>)delegate;
|
|
||||||
|
|
||||||
+(NSDictionary *)getAccessTokenMeta;
|
|
||||||
|
|
||||||
-(NSString *)checkAuth;
|
|
||||||
-(void)checkAuth:(HPAPICheckAuthCompletionHandler)completionHandler;
|
|
||||||
-(NSString *)save:(NSURL *)url;
|
|
||||||
-(BOOL)save:(NSURL *)url completionHandler:(HPRPCClientCompletionHandler)completionHandler;
|
|
||||||
|
|
||||||
@end
|
|
||||||
|
|
||||||
NS_ASSUME_NONNULL_END
|
|
|
@ -1,145 +0,0 @@
|
||||||
//
|
|
||||||
// HPAPI.m
|
|
||||||
// HotPocket
|
|
||||||
//
|
|
||||||
// Created by Tomek Wójcik on 23/09/2025.
|
|
||||||
//
|
|
||||||
|
|
||||||
#import "HPAPI.h"
|
|
||||||
|
|
||||||
#import "HPCredentialsHelper.h"
|
|
||||||
#import "HPRPCClient.h"
|
|
||||||
|
|
||||||
@implementation HPAPI (HPAPIPrivate)
|
|
||||||
|
|
||||||
#pragma mark - Private interface
|
|
||||||
|
|
||||||
-(void)updateRPCClientCredentials {
|
|
||||||
HPCredentials *credentials = [[HPCredentialsHelper sharedHelper] getCredentials];
|
|
||||||
self.rpcClient.baseURL = credentials.rpcURL;
|
|
||||||
self.rpcClient.accessToken = credentials.accessToken;
|
|
||||||
}
|
|
||||||
|
|
||||||
@end
|
|
||||||
|
|
||||||
@implementation HPAPI
|
|
||||||
|
|
||||||
#pragma mark - Initialization
|
|
||||||
|
|
||||||
-(id)init {
|
|
||||||
if (self = [super init]) {
|
|
||||||
self.rpcClient = [[HPRPCClient alloc] initWithBaseURL:nil accessToken:nil];
|
|
||||||
|
|
||||||
[self updateRPCClientCredentials];
|
|
||||||
|
|
||||||
[[NSNotificationCenter defaultCenter] addObserver:self
|
|
||||||
selector:@selector(onCredentialsChanged:)
|
|
||||||
name:@"HPCredentialsChanged"
|
|
||||||
object:nil];
|
|
||||||
}
|
|
||||||
|
|
||||||
return self;
|
|
||||||
}
|
|
||||||
|
|
||||||
-(id)initWithRPCClientDelegate:(id<HPRPCClientDelegate>)rpcClientDelegate {
|
|
||||||
if (self = [self init]) {
|
|
||||||
self.rpcClient.delegate = rpcClientDelegate;
|
|
||||||
}
|
|
||||||
|
|
||||||
return self;
|
|
||||||
}
|
|
||||||
|
|
||||||
-(void)dealloc {
|
|
||||||
[[NSNotificationCenter defaultCenter] removeObserver:self];
|
|
||||||
}
|
|
||||||
|
|
||||||
#pragma mark - Public interface
|
|
||||||
|
|
||||||
+(NSDictionary *)getAccessTokenMeta {
|
|
||||||
NSBundle *mainBundle = [NSBundle mainBundle];
|
|
||||||
|
|
||||||
return @{
|
|
||||||
@"version": [mainBundle.infoDictionary valueForKey:@"CFBundleShortVersionString"],
|
|
||||||
@"platform": [mainBundle.infoDictionary valueForKey:@"HPAPIAccessTokenPlatform"],
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
-(NSString *)checkAuth {
|
|
||||||
if (self.rpcClient.hasCredentials == NO) {
|
|
||||||
return nil;
|
|
||||||
}
|
|
||||||
|
|
||||||
NSString *callId = [[NSUUID UUID] UUIDString];
|
|
||||||
|
|
||||||
BOOL callResult = [self.rpcClient call:callId
|
|
||||||
method:@"accounts.auth.check_access_token"
|
|
||||||
params:@[self.rpcClient.accessToken, [HPAPI getAccessTokenMeta]]
|
|
||||||
endopoint:@"/accounts/rpc/"];
|
|
||||||
if (callResult == NO) {
|
|
||||||
return nil;
|
|
||||||
}
|
|
||||||
|
|
||||||
return callId;
|
|
||||||
}
|
|
||||||
|
|
||||||
-(void)checkAuth:(HPAPICheckAuthCompletionHandler)completionHandler {
|
|
||||||
if (self.rpcClient.hasCredentials == NO) {
|
|
||||||
completionHandler(NO, nil, nil);
|
|
||||||
} else {
|
|
||||||
NSString *callId = [[NSUUID UUID] UUIDString];
|
|
||||||
BOOL callResult = [self.rpcClient call:callId
|
|
||||||
method:@"accounts.auth.check_access_token"
|
|
||||||
params:@[self.rpcClient.accessToken, [HPAPI getAccessTokenMeta]]
|
|
||||||
endopoint:@"/accounts/rpc/" completionHandler:^(NSString *finalCallId, HPRPCCallResult *result) {
|
|
||||||
BOOL authValid = YES;
|
|
||||||
if (result.error != nil) {
|
|
||||||
authValid = NO;
|
|
||||||
} else if ([(NSNumber *)result.result boolValue] == NO) {
|
|
||||||
authValid = NO;
|
|
||||||
}
|
|
||||||
|
|
||||||
completionHandler(authValid, result.error, finalCallId);
|
|
||||||
}];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
-(NSString *)save:(NSURL *)url {
|
|
||||||
if (self.rpcClient.hasCredentials == NO) {
|
|
||||||
return nil;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (url == nil) {
|
|
||||||
return nil;
|
|
||||||
}
|
|
||||||
|
|
||||||
NSString *callId = [[NSUUID UUID] UUIDString];
|
|
||||||
BOOL callResult = [self.rpcClient call:callId method:@"saves.create" params:@[[url absoluteString]]];
|
|
||||||
if (callResult == NO) {
|
|
||||||
return nil;
|
|
||||||
}
|
|
||||||
|
|
||||||
return callId;
|
|
||||||
}
|
|
||||||
|
|
||||||
-(BOOL)save:(NSURL *)url completionHandler:(HPRPCClientCompletionHandler)completionHandler {
|
|
||||||
if (self.rpcClient.hasCredentials == NO) {
|
|
||||||
return NO;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (url == nil) {
|
|
||||||
return NO;
|
|
||||||
}
|
|
||||||
|
|
||||||
NSString *callId = [[NSUUID UUID] UUIDString];
|
|
||||||
return [self.rpcClient call:callId
|
|
||||||
method:@"saves.create"
|
|
||||||
params:@[[url absoluteString]]
|
|
||||||
completionHandler:completionHandler];
|
|
||||||
}
|
|
||||||
|
|
||||||
#pragma mark - Notification handlers
|
|
||||||
|
|
||||||
-(void)onCredentialsChanged:(NSNotification *)notification {
|
|
||||||
[self updateRPCClientCredentials];
|
|
||||||
}
|
|
||||||
@end
|
|
|
@ -1,30 +0,0 @@
|
||||||
//
|
|
||||||
// HPAuthFlow.h
|
|
||||||
// HotPocket (macOS)
|
|
||||||
//
|
|
||||||
// Created by Tomek Wójcik on 21/09/2025.
|
|
||||||
//
|
|
||||||
|
|
||||||
#import <Foundation/Foundation.h>
|
|
||||||
|
|
||||||
NS_ASSUME_NONNULL_BEGIN
|
|
||||||
|
|
||||||
@interface HPAuthParams : NSObject
|
|
||||||
|
|
||||||
@property (copy) NSString *authKey;
|
|
||||||
@property (copy) NSString *sessionToken;
|
|
||||||
|
|
||||||
@end
|
|
||||||
|
|
||||||
@interface HPAuthFlow : NSObject
|
|
||||||
|
|
||||||
@property (nullable) NSURL *baseURL;
|
|
||||||
@property (nullable) NSString *sessionToken;
|
|
||||||
|
|
||||||
-(NSURL *)start;
|
|
||||||
-(HPAuthParams *)handlePostAuthenticateURL:(NSURL *)url;
|
|
||||||
-(BOOL)handleAuthParams:(HPAuthParams *)authParams;
|
|
||||||
|
|
||||||
@end
|
|
||||||
|
|
||||||
NS_ASSUME_NONNULL_END
|
|
|
@ -1,140 +0,0 @@
|
||||||
//
|
|
||||||
// HPAuthFlow.m
|
|
||||||
// HotPocket (macOS)
|
|
||||||
//
|
|
||||||
// Created by Tomek Wójcik on 21/09/2025.
|
|
||||||
//
|
|
||||||
|
|
||||||
#import "HPAuthFlow.h"
|
|
||||||
|
|
||||||
#import "HPAPI.h"
|
|
||||||
#import "HPCredentialsHelper.h"
|
|
||||||
#import "HPRPCClient.h"
|
|
||||||
#import "NSURL+HotPocketExtensions.h"
|
|
||||||
|
|
||||||
@implementation HPAuthParams
|
|
||||||
|
|
||||||
#pragma mark - HPAuthParams implementation
|
|
||||||
|
|
||||||
@end
|
|
||||||
|
|
||||||
@implementation HPAuthFlow (HPAuthFlowPrivate)
|
|
||||||
|
|
||||||
#pragma mark - HPAuthFlow private interface
|
|
||||||
|
|
||||||
-(NSURL *)resolveAuthenticateURL {
|
|
||||||
if (self.baseURL == nil) {
|
|
||||||
return nil;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (self.baseURL.isUsableInHotPocket == NO) {
|
|
||||||
return nil;
|
|
||||||
}
|
|
||||||
|
|
||||||
NSBundle *mainBundle = [NSBundle mainBundle];
|
|
||||||
|
|
||||||
NSURLComponents *authURLComponents = [NSURLComponents componentsWithURL:self.baseURL resolvingAgainstBaseURL:NO];
|
|
||||||
authURLComponents.path = @"/integrations/extension/authenticate/";
|
|
||||||
authURLComponents.queryItems = @[
|
|
||||||
[NSURLQueryItem queryItemWithName:@"source" value:[[mainBundle infoDictionary] valueForKey:@"HPAuthFlowSource"]],
|
|
||||||
[NSURLQueryItem queryItemWithName:@"session_token" value:self.sessionToken],
|
|
||||||
];
|
|
||||||
|
|
||||||
return authURLComponents.URL;
|
|
||||||
}
|
|
||||||
|
|
||||||
@end
|
|
||||||
|
|
||||||
@implementation HPAuthFlow
|
|
||||||
|
|
||||||
#pragma mark - Initialization
|
|
||||||
|
|
||||||
-(id)init {
|
|
||||||
if (self = [super init]) {
|
|
||||||
self.baseURL = nil;
|
|
||||||
self.sessionToken = nil;
|
|
||||||
}
|
|
||||||
|
|
||||||
return self;
|
|
||||||
}
|
|
||||||
|
|
||||||
#pragma mark - Public interface
|
|
||||||
|
|
||||||
-(NSURL *)start {
|
|
||||||
if (self.baseURL == nil) {
|
|
||||||
return nil;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (self.sessionToken == nil) {
|
|
||||||
self.sessionToken = [[NSUUID UUID] UUIDString];
|
|
||||||
}
|
|
||||||
|
|
||||||
return [self resolveAuthenticateURL];
|
|
||||||
}
|
|
||||||
|
|
||||||
-(HPAuthParams *)handlePostAuthenticateURL:(NSURL *)url {
|
|
||||||
if (url == nil) {
|
|
||||||
return nil;
|
|
||||||
}
|
|
||||||
|
|
||||||
NSDictionary *postAuthenticateURLParams = [[[NSBundle mainBundle] infoDictionary] valueForKey:@"HPAuthFlowPostAuthenticateURLParts"];
|
|
||||||
if (postAuthenticateURLParams == nil) {
|
|
||||||
return nil;
|
|
||||||
}
|
|
||||||
|
|
||||||
NSURLComponents *urlComponents = [NSURLComponents componentsWithURL:url resolvingAgainstBaseURL:NO];
|
|
||||||
|
|
||||||
if ([urlComponents.scheme isEqualToString:[postAuthenticateURLParams valueForKey:@"scheme"]] == NO) {
|
|
||||||
return nil;
|
|
||||||
}
|
|
||||||
|
|
||||||
if ([urlComponents.host isEqualToString:[postAuthenticateURLParams valueForKey:@"host"]] == NO) {
|
|
||||||
return nil;
|
|
||||||
}
|
|
||||||
|
|
||||||
HPAuthParams *result = [[HPAuthParams alloc] init];
|
|
||||||
for (NSURLQueryItem *queryItem in urlComponents.queryItems) {
|
|
||||||
if ([queryItem.name isEqualToString:@"auth_key"] == YES) {
|
|
||||||
result.authKey = queryItem.value;
|
|
||||||
} else if ([queryItem.name isEqualToString:@"session_token"] == YES) {
|
|
||||||
result.sessionToken = queryItem.value;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if ([self.sessionToken isEqualToString:result.sessionToken] == NO) {
|
|
||||||
return nil;
|
|
||||||
}
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
-(BOOL)handleAuthParams:(HPAuthParams *)authParams {
|
|
||||||
HPRPCClient *rpcClient = [[HPRPCClient alloc] initWithBaseURL:self.baseURL accessToken:nil];
|
|
||||||
|
|
||||||
NSArray *callParams = @[
|
|
||||||
authParams.authKey,
|
|
||||||
[HPAPI getAccessTokenMeta],
|
|
||||||
];
|
|
||||||
|
|
||||||
BOOL callResult = [rpcClient call:self.sessionToken
|
|
||||||
method:@"accounts.access_tokens.create"
|
|
||||||
params:callParams endopoint:@"/accounts/rpc/"
|
|
||||||
completionHandler:^(NSString *callId, HPRPCCallResult *result) {
|
|
||||||
dispatch_async(dispatch_get_main_queue(), ^{
|
|
||||||
if (result.error != nil) {
|
|
||||||
NSLog(@"-[HPAuthFlow handleAuthParams:] error=`%@`", result.error);
|
|
||||||
} else {
|
|
||||||
HPCredentialsHelper *credentialsHelper = [HPCredentialsHelper sharedHelper];
|
|
||||||
[credentialsHelper saveCredentials:[self.baseURL absoluteString] accessToken:(NSString *)result.result];
|
|
||||||
}
|
|
||||||
|
|
||||||
self.sessionToken = nil;
|
|
||||||
|
|
||||||
[[NSNotificationCenter defaultCenter] postNotificationName:@"AuthFlowDidFinish" object:self];
|
|
||||||
});
|
|
||||||
}];
|
|
||||||
|
|
||||||
return callResult;
|
|
||||||
}
|
|
||||||
|
|
||||||
@end
|
|
|
@ -1,32 +0,0 @@
|
||||||
//
|
|
||||||
// HPCredentialsHelper.h
|
|
||||||
// HotPocket
|
|
||||||
//
|
|
||||||
// Created by Tomek Wójcik on 19/09/2025.
|
|
||||||
//
|
|
||||||
|
|
||||||
#import <Foundation/Foundation.h>
|
|
||||||
|
|
||||||
NS_ASSUME_NONNULL_BEGIN
|
|
||||||
|
|
||||||
@interface HPCredentials : NSObject
|
|
||||||
|
|
||||||
@property (nullable) NSString *baseURL;
|
|
||||||
@property (nullable) NSString *accessToken;
|
|
||||||
|
|
||||||
@property (readonly) BOOL usable;
|
|
||||||
@property (readonly) NSURL *rpcURL;
|
|
||||||
|
|
||||||
@end
|
|
||||||
|
|
||||||
@interface HPCredentialsHelper : NSObject
|
|
||||||
|
|
||||||
+(instancetype)sharedHelper;
|
|
||||||
|
|
||||||
-(HPCredentials *)getCredentials;
|
|
||||||
-(BOOL)saveCredentials:(NSString *)baseURL accessToken:(NSString *)accessToken;
|
|
||||||
-(BOOL)clearCredentials;
|
|
||||||
|
|
||||||
@end
|
|
||||||
|
|
||||||
NS_ASSUME_NONNULL_END
|
|
|
@ -1,218 +0,0 @@
|
||||||
//
|
|
||||||
// HPCredentialsHelper.m
|
|
||||||
// HotPocket
|
|
||||||
//
|
|
||||||
// Created by Tomek Wójcik on 19/09/2025.
|
|
||||||
//
|
|
||||||
|
|
||||||
#import <Security/Security.h>
|
|
||||||
|
|
||||||
#import "HPCredentialsHelper.h"
|
|
||||||
|
|
||||||
@implementation HPCredentials
|
|
||||||
|
|
||||||
#pragma mark - HPCredentials implementation
|
|
||||||
|
|
||||||
-(id)init {
|
|
||||||
if (self = [super init]) {
|
|
||||||
self.baseURL = nil;
|
|
||||||
self.accessToken = nil;
|
|
||||||
}
|
|
||||||
|
|
||||||
return self;
|
|
||||||
}
|
|
||||||
|
|
||||||
-(BOOL)usable {
|
|
||||||
return (self.baseURL != nil && self.accessToken != nil);
|
|
||||||
}
|
|
||||||
|
|
||||||
-(NSURL *)rpcURL {
|
|
||||||
return [NSURL URLWithString:self.baseURL];
|
|
||||||
}
|
|
||||||
|
|
||||||
-(NSString *)description {
|
|
||||||
NSMutableDictionary *attributes = [NSMutableDictionary dictionaryWithCapacity:2];
|
|
||||||
|
|
||||||
if (self.baseURL == nil) {
|
|
||||||
[attributes setValue:@"(null)" forKey:@"baseURL"];
|
|
||||||
} else {
|
|
||||||
[attributes setValue:self.baseURL forKey:@"baseURL"];
|
|
||||||
}
|
|
||||||
|
|
||||||
if (self.accessToken == nil) {
|
|
||||||
[attributes setValue:@"(null)" forKey:@"accessToken"];
|
|
||||||
} else {
|
|
||||||
[attributes setValue:@"***" forKey:@"accessToken"];
|
|
||||||
}
|
|
||||||
|
|
||||||
return [NSString stringWithFormat:@"<%@: %p; %@>", NSStringFromClass([self class]), self, attributes];
|
|
||||||
}
|
|
||||||
|
|
||||||
@end
|
|
||||||
|
|
||||||
@implementation HPCredentialsHelper (HPCredentialsHelperPrivate)
|
|
||||||
|
|
||||||
#pragma mark - Private interface
|
|
||||||
|
|
||||||
-(NSString *)getService {
|
|
||||||
#ifdef DEBUG
|
|
||||||
return @"pl.bthlabs.HotPocket.Debug";
|
|
||||||
#else
|
|
||||||
return @"pl.bthlabs.HotPocket";
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
|
|
||||||
-(NSData *)getKeychainItem:(NSString *)service account:(NSString *)account {
|
|
||||||
if (service == nil || account == nil) {
|
|
||||||
return nil;
|
|
||||||
}
|
|
||||||
|
|
||||||
NSDictionary *query = @{
|
|
||||||
(__bridge id)kSecClass: (__bridge id)kSecClassGenericPassword,
|
|
||||||
(__bridge id)kSecAttrService: service,
|
|
||||||
(__bridge id)kSecAttrAccount: account,
|
|
||||||
(__bridge id)kSecReturnData: @YES,
|
|
||||||
(__bridge id)kSecMatchLimit: (__bridge id)kSecMatchLimitOne,
|
|
||||||
(__bridge id)kSecAttrAccessGroup: @"648728X64K.pl.bthlabs.HotPocketShared",
|
|
||||||
(__bridge id)kSecUseDataProtectionKeychain: @YES,
|
|
||||||
};
|
|
||||||
|
|
||||||
CFTypeRef resultData = NULL;
|
|
||||||
OSStatus status = SecItemCopyMatching((__bridge CFDictionaryRef)query, &resultData);
|
|
||||||
|
|
||||||
if (status == errSecSuccess && resultData != NULL) {
|
|
||||||
NSData *result = (__bridge_transfer NSData *)resultData;
|
|
||||||
return result;
|
|
||||||
} else {
|
|
||||||
CFStringRef statusStringRef = SecCopyErrorMessageString(status, NULL);
|
|
||||||
NSString *statusString = (__bridge NSString *)statusStringRef;
|
|
||||||
NSLog(@"-[HPCredentialsHelper getKeychainItem:account:] service=`%@` account=`%@` status=%@", service, account, statusString);
|
|
||||||
return nil;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
-(BOOL)createKeychainItemWithValue:(NSData *)value service:(NSString *)service account:(NSString *)account {
|
|
||||||
if (value == nil || service == nil || account == nil) {
|
|
||||||
return NO;
|
|
||||||
}
|
|
||||||
|
|
||||||
NSDictionary *attributes = @{
|
|
||||||
(__bridge id)kSecClass: (__bridge id)kSecClassGenericPassword,
|
|
||||||
(__bridge id)kSecAttrService: service,
|
|
||||||
(__bridge id)kSecAttrAccount: account,
|
|
||||||
(__bridge id)kSecValueData: value,
|
|
||||||
(__bridge id)kSecAttrAccessGroup: @"648728X64K.pl.bthlabs.HotPocketShared",
|
|
||||||
(__bridge id)kSecUseDataProtectionKeychain: @YES,
|
|
||||||
};
|
|
||||||
|
|
||||||
OSStatus status = SecItemAdd((__bridge CFDictionaryRef)attributes, NULL);
|
|
||||||
|
|
||||||
if (status != errSecSuccess) {
|
|
||||||
CFStringRef statusStringRef = SecCopyErrorMessageString(status, NULL);
|
|
||||||
NSString *statusString = (__bridge NSString *)statusStringRef;
|
|
||||||
NSLog(@"-[HPCredentialsHelper createKeychainItemWithValue:service:account:] service=`%@` account=`%@` status=%@", service, account, statusString);
|
|
||||||
return NO;
|
|
||||||
}
|
|
||||||
|
|
||||||
return YES;
|
|
||||||
}
|
|
||||||
|
|
||||||
-(BOOL)deleteKeychainItem:(NSString *)service account:(NSString *)account {
|
|
||||||
if (service == nil || account == nil) {
|
|
||||||
return NO;
|
|
||||||
}
|
|
||||||
|
|
||||||
NSDictionary *query = @{
|
|
||||||
(__bridge id)kSecClass: (__bridge id)kSecClassGenericPassword,
|
|
||||||
(__bridge id)kSecAttrService: service,
|
|
||||||
(__bridge id)kSecAttrAccount: account,
|
|
||||||
(__bridge id)kSecAttrAccessGroup: @"648728X64K.pl.bthlabs.HotPocketShared",
|
|
||||||
(__bridge id)kSecUseDataProtectionKeychain: @YES,
|
|
||||||
};
|
|
||||||
|
|
||||||
OSStatus status = SecItemDelete((__bridge CFDictionaryRef)query);
|
|
||||||
|
|
||||||
if (status != errSecSuccess) {
|
|
||||||
CFStringRef statusStringRef = SecCopyErrorMessageString(status, NULL);
|
|
||||||
NSString *statusString = (__bridge NSString *)statusStringRef;
|
|
||||||
NSLog(@"-[HPCredentialsHelper deleteKeychainItem:account:] service=`%@` account=`%@` status=%@", service, account, statusString);
|
|
||||||
return NO;
|
|
||||||
}
|
|
||||||
|
|
||||||
return YES;
|
|
||||||
}
|
|
||||||
|
|
||||||
@end
|
|
||||||
|
|
||||||
@implementation HPCredentialsHelper
|
|
||||||
|
|
||||||
#pragma mark - Initialization
|
|
||||||
|
|
||||||
+(instancetype)sharedHelper {
|
|
||||||
static HPCredentialsHelper *sharedInstance = nil;
|
|
||||||
static dispatch_once_t initToken;
|
|
||||||
dispatch_once(&initToken, ^{
|
|
||||||
sharedInstance = [[self alloc] init];
|
|
||||||
});
|
|
||||||
|
|
||||||
return sharedInstance;
|
|
||||||
}
|
|
||||||
|
|
||||||
#pragma mark - Public interface
|
|
||||||
|
|
||||||
-(HPCredentials *)getCredentials {
|
|
||||||
HPCredentials *result = [[HPCredentials alloc] init];
|
|
||||||
|
|
||||||
NSData *itemData = [self getKeychainItem:[self getService] account:@"RPC"];
|
|
||||||
if (itemData != nil) {
|
|
||||||
NSError *error;
|
|
||||||
NSDictionary *itemPayload = [NSJSONSerialization JSONObjectWithData:itemData
|
|
||||||
options:NSJSONReadingTopLevelDictionaryAssumed
|
|
||||||
error:&error];
|
|
||||||
|
|
||||||
if (error != nil) {
|
|
||||||
NSLog(@"-[HPCredentialsHalper getCredentials] error=`%@`", error);
|
|
||||||
} else if (itemPayload != nil) {
|
|
||||||
result.baseURL = [itemPayload valueForKey:@"baseURL"];
|
|
||||||
result.accessToken = [itemPayload valueForKey:@"accessToken"];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
-(BOOL)saveCredentials:(NSString *)baseURL accessToken:(NSString *)accessToken {
|
|
||||||
NSMutableDictionary *itemPayload = [NSMutableDictionary dictionaryWithCapacity:2];
|
|
||||||
|
|
||||||
if (baseURL != nil) {
|
|
||||||
[itemPayload setValue:baseURL forKey:@"baseURL"];
|
|
||||||
}
|
|
||||||
|
|
||||||
if (accessToken != nil) {
|
|
||||||
[itemPayload setValue:accessToken forKey:@"accessToken"];
|
|
||||||
}
|
|
||||||
|
|
||||||
NSError *error;
|
|
||||||
NSData *itemData = [NSJSONSerialization dataWithJSONObject:itemPayload options:0 error:&error];
|
|
||||||
|
|
||||||
if (error != nil) {
|
|
||||||
NSLog(@"-[HPCredentialsHalper saveCredentials:accessToken:] error=`%@`", error);
|
|
||||||
return NO;
|
|
||||||
}
|
|
||||||
|
|
||||||
BOOL saveResult = [self createKeychainItemWithValue:itemData service:[self getService] account:@"RPC"];
|
|
||||||
|
|
||||||
[[NSNotificationCenter defaultCenter] postNotificationName:@"HPCredentialsChanged" object:self];
|
|
||||||
|
|
||||||
return saveResult;
|
|
||||||
}
|
|
||||||
|
|
||||||
-(BOOL)clearCredentials {
|
|
||||||
BOOL deleteResult = [self deleteKeychainItem:[self getService] account:@"RPC"];
|
|
||||||
|
|
||||||
[[NSNotificationCenter defaultCenter] postNotificationName:@"HPCredentialsChanged" object:self];
|
|
||||||
|
|
||||||
return deleteResult;
|
|
||||||
}
|
|
||||||
|
|
||||||
@end
|
|
|
@ -1,44 +0,0 @@
|
||||||
//
|
|
||||||
// HPRPCClient.h
|
|
||||||
// HotPocket
|
|
||||||
//
|
|
||||||
// Created by Tomek Wójcik on 19/09/2025.
|
|
||||||
//
|
|
||||||
|
|
||||||
#import <Foundation/Foundation.h>
|
|
||||||
|
|
||||||
NS_ASSUME_NONNULL_BEGIN
|
|
||||||
|
|
||||||
@interface HPRPCCallResult : NSObject
|
|
||||||
|
|
||||||
@property (nullable) NSError *error;
|
|
||||||
@property (nullable) id result;
|
|
||||||
|
|
||||||
@end
|
|
||||||
|
|
||||||
@protocol HPRPCClientDelegate <NSObject>
|
|
||||||
|
|
||||||
-(void)rpcClientDidReceiveResult:(HPRPCCallResult *)result callId:(NSString *)callId;
|
|
||||||
|
|
||||||
@end
|
|
||||||
|
|
||||||
typedef void (^HPRPCClientCompletionHandler)(NSString * _Nullable callId, HPRPCCallResult * _Nullable result);
|
|
||||||
|
|
||||||
@interface HPRPCClient : NSObject
|
|
||||||
|
|
||||||
@property (nonatomic, weak) id<HPRPCClientDelegate> delegate;
|
|
||||||
@property NSURL *baseURL;
|
|
||||||
@property NSString *accessToken;
|
|
||||||
@property NSURLSession *session;
|
|
||||||
|
|
||||||
-(id)initWithBaseURL:(nullable NSURL *)baseURL accessToken:(nullable NSString *)accessToken;
|
|
||||||
|
|
||||||
-(BOOL)hasCredentials;
|
|
||||||
-(BOOL)call:(nullable NSString *)callId method:(NSString *)method params:(NSArray *)params endopoint:(nullable NSString *)endpoint completionHandler:(HPRPCClientCompletionHandler)completionHandler;
|
|
||||||
-(BOOL)call:(nullable NSString *)callId method:(NSString *)method params:(NSArray *)params endopoint:(nullable NSString *)endpoint;
|
|
||||||
-(BOOL)call:(nullable NSString *)callId method:(NSString *)method params:(NSArray *)params;
|
|
||||||
-(BOOL)call:(nullable NSString *)callId method:(NSString *)method params:(NSArray *)params completionHandler:(HPRPCClientCompletionHandler)completionHandler;
|
|
||||||
|
|
||||||
@end
|
|
||||||
|
|
||||||
NS_ASSUME_NONNULL_END
|
|
|
@ -1,186 +0,0 @@
|
||||||
//
|
|
||||||
// HPRPCClient.m
|
|
||||||
// HotPocket
|
|
||||||
//
|
|
||||||
// Created by Tomek Wójcik on 19/09/2025.
|
|
||||||
//
|
|
||||||
|
|
||||||
#import "HPRPCClient.h"
|
|
||||||
|
|
||||||
@implementation HPRPCCallResult
|
|
||||||
|
|
||||||
#pragma mark - HPRPCCallResult implementation
|
|
||||||
|
|
||||||
-(id)init {
|
|
||||||
if (self = [super init]) {
|
|
||||||
self.error = nil;
|
|
||||||
self.result = nil;
|
|
||||||
}
|
|
||||||
|
|
||||||
return self;
|
|
||||||
}
|
|
||||||
|
|
||||||
-(NSString *)description {
|
|
||||||
NSMutableDictionary *attributes = [NSMutableDictionary dictionaryWithCapacity:2];
|
|
||||||
|
|
||||||
if (self.error == nil) {
|
|
||||||
[attributes setValue:@"(null)" forKey:@"error"];
|
|
||||||
} else {
|
|
||||||
[attributes setValue:self.error forKey:@"error"];
|
|
||||||
}
|
|
||||||
|
|
||||||
if (self.result == nil) {
|
|
||||||
[attributes setValue:@"(null)" forKey:@"result"];
|
|
||||||
} else {
|
|
||||||
[attributes setValue:self.result forKey:@"result"];
|
|
||||||
}
|
|
||||||
|
|
||||||
return [NSString stringWithFormat:@"<%@: %p; %@>", NSStringFromClass([self class]), self, attributes];
|
|
||||||
}
|
|
||||||
|
|
||||||
@end
|
|
||||||
|
|
||||||
@implementation HPRPCClient
|
|
||||||
|
|
||||||
#pragma mark - Initialization
|
|
||||||
|
|
||||||
-(id)initWithBaseURL:(nullable NSURL *)baseURL accessToken:(nullable NSString *)accessToken {
|
|
||||||
if (self = [super init]) {
|
|
||||||
self.baseURL = baseURL;
|
|
||||||
self.accessToken = accessToken;
|
|
||||||
self.session = [NSURLSession sessionWithConfiguration:NSURLSessionConfiguration.ephemeralSessionConfiguration];
|
|
||||||
}
|
|
||||||
|
|
||||||
return self;
|
|
||||||
}
|
|
||||||
|
|
||||||
#pragma mark - Public interface
|
|
||||||
|
|
||||||
-(BOOL)hasCredentials {
|
|
||||||
return (self.baseURL != nil && self.accessToken != nil);
|
|
||||||
}
|
|
||||||
|
|
||||||
-(BOOL)call:(nullable NSString *)callId method:(NSString *)method params:(NSArray *)params endopoint:(nullable NSString *)endpoint completionHandler:(HPRPCClientCompletionHandler)completionHandler {
|
|
||||||
if (self.baseURL == nil) {
|
|
||||||
return NO;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (callId == nil) {
|
|
||||||
callId = [[NSUUID UUID] UUIDString];
|
|
||||||
}
|
|
||||||
|
|
||||||
if (endpoint == nil) {
|
|
||||||
endpoint = @"/rpc/";
|
|
||||||
}
|
|
||||||
|
|
||||||
NSBundle *mainBundle = [NSBundle mainBundle];
|
|
||||||
|
|
||||||
NSDictionary *payload = @{
|
|
||||||
@"jsonrpc": @"2.0",
|
|
||||||
@"id": callId,
|
|
||||||
@"method": method,
|
|
||||||
@"params": params,
|
|
||||||
};
|
|
||||||
|
|
||||||
NSError *error;
|
|
||||||
NSData *jsonPayload = [NSJSONSerialization dataWithJSONObject:payload options:0 error:&error];
|
|
||||||
if (!jsonPayload) {
|
|
||||||
NSLog(@"-[HPRPCClient call:method:params:endpoint:] Unable to serialize payload: error=`%@`", error);
|
|
||||||
HPRPCCallResult *result = [[HPRPCCallResult alloc] init];
|
|
||||||
result.error = error;
|
|
||||||
|
|
||||||
if (self.delegate != nil) {
|
|
||||||
[self.delegate rpcClientDidReceiveResult:result callId:callId];
|
|
||||||
}
|
|
||||||
|
|
||||||
return NO;
|
|
||||||
}
|
|
||||||
|
|
||||||
NSURLComponents *urlComponents = [NSURLComponents componentsWithURL:self.baseURL resolvingAgainstBaseURL:NO];
|
|
||||||
urlComponents.path = endpoint;
|
|
||||||
urlComponents.queryItems = @[
|
|
||||||
[NSURLQueryItem queryItemWithName:@"method" value:method],
|
|
||||||
];
|
|
||||||
|
|
||||||
NSURL *callURL = [urlComponents URL];
|
|
||||||
#ifdef DEBUG
|
|
||||||
NSLog(@"-[HPRPCClient call:method:params:endpoint:] callURL=`%@`", callURL.absoluteString);
|
|
||||||
#endif
|
|
||||||
|
|
||||||
NSMutableURLRequest *request = [[NSMutableURLRequest alloc] initWithURL:callURL];
|
|
||||||
request.HTTPMethod = @"POST";
|
|
||||||
request.HTTPBody = jsonPayload;
|
|
||||||
|
|
||||||
[request setValue:@"application/json;charset=utf-8" forHTTPHeaderField:@"Content-Type"];
|
|
||||||
[request setValue:[[mainBundle infoDictionary] valueForKey:@"HPRPCClientOrigin"] forHTTPHeaderField:@"Origin"];
|
|
||||||
|
|
||||||
if (self.accessToken != nil) {
|
|
||||||
NSString *authorization = [NSString stringWithFormat:@"Bearer %@", self.accessToken];
|
|
||||||
[request setValue:authorization forHTTPHeaderField:@"Authorization"];
|
|
||||||
}
|
|
||||||
|
|
||||||
NSString *build = [[NSBundle mainBundle] objectForInfoDictionaryKey:@"CFBundleVersion"];
|
|
||||||
NSString *userAgent = [NSString stringWithFormat:@"HotPocket/%@", build];
|
|
||||||
[request setValue:userAgent forHTTPHeaderField:@"User-Agent"];
|
|
||||||
|
|
||||||
NSURLSessionDataTask *task = [self.session dataTaskWithRequest:request
|
|
||||||
completionHandler:^(NSData *data, NSURLResponse *response, NSError *error) {
|
|
||||||
HPRPCCallResult *result = [[HPRPCCallResult alloc] init];
|
|
||||||
if (error != nil) {
|
|
||||||
result.error = error;
|
|
||||||
} else {
|
|
||||||
NSHTTPURLResponse *httpResponse = (NSHTTPURLResponse *)response;
|
|
||||||
if (httpResponse.statusCode != 200) {
|
|
||||||
result.error = [[NSError alloc] initWithDomain:@"pl.bthlabs.HotPocket.HPRPCClient" code:-32000 userInfo:@{
|
|
||||||
@"callId": callId,
|
|
||||||
@"url": httpResponse.URL,
|
|
||||||
@"statusCode": [NSNumber numberWithInteger:httpResponse.statusCode],
|
|
||||||
@"response": response,
|
|
||||||
}];
|
|
||||||
} else {
|
|
||||||
NSError *jsonDecodeError;
|
|
||||||
NSDictionary *callResult = [NSJSONSerialization JSONObjectWithData:data options:NSJSONReadingTopLevelDictionaryAssumed error:&error];
|
|
||||||
if (jsonDecodeError != nil) {
|
|
||||||
result.error = jsonDecodeError;
|
|
||||||
} else {
|
|
||||||
NSDictionary *rpcError = [callResult valueForKey:@"error"];
|
|
||||||
if (rpcError != nil) {
|
|
||||||
NSNumber *rpcErrorCode = [rpcError valueForKey:@"code"];
|
|
||||||
if (rpcErrorCode == nil) {
|
|
||||||
rpcErrorCode = [NSNumber numberWithInt:-32000];
|
|
||||||
}
|
|
||||||
|
|
||||||
result.error = [[NSError alloc] initWithDomain:@"pl.bthlabs.HotPocket.HPRPCClient" code:[rpcErrorCode integerValue] userInfo:rpcError];
|
|
||||||
} else {
|
|
||||||
result.result = [callResult valueForKey:@"result"];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (completionHandler) {
|
|
||||||
completionHandler(callId, result);
|
|
||||||
}
|
|
||||||
}];
|
|
||||||
[task resume];
|
|
||||||
|
|
||||||
return YES;
|
|
||||||
}
|
|
||||||
|
|
||||||
-(BOOL)call:(nullable NSString *)callId method:(NSString *)method params:(NSArray *)params endopoint:(nullable NSString *)endpoint {
|
|
||||||
return [self call:callId method:method params:params endopoint:endpoint completionHandler:^(NSString *callId, HPRPCCallResult *result) {
|
|
||||||
if (self.delegate != nil) {
|
|
||||||
[self.delegate rpcClientDidReceiveResult:result callId:callId];
|
|
||||||
}
|
|
||||||
}];
|
|
||||||
}
|
|
||||||
|
|
||||||
-(BOOL)call:(nullable NSString *)callId method:(NSString *)method params:(NSArray *)params {
|
|
||||||
return [self call:callId method:method params:params endopoint:nil];
|
|
||||||
}
|
|
||||||
|
|
||||||
-(BOOL)call:(nullable NSString *)callId method:(NSString *)method params:(NSArray *)params completionHandler:(HPRPCClientCompletionHandler)completionHandler {
|
|
||||||
return [self call:callId method:method params:params endopoint:nil completionHandler:completionHandler];
|
|
||||||
}
|
|
||||||
|
|
||||||
@end
|
|
|
@ -1,18 +0,0 @@
|
||||||
//
|
|
||||||
// NSURL+HotPocketExtensions.h
|
|
||||||
// HotPocket (macOS)
|
|
||||||
//
|
|
||||||
// Created by Tomek Wójcik on 30/09/2025.
|
|
||||||
//
|
|
||||||
|
|
||||||
#import <Foundation/Foundation.h>
|
|
||||||
|
|
||||||
NS_ASSUME_NONNULL_BEGIN
|
|
||||||
|
|
||||||
@interface NSURL (HotPocketExtensions)
|
|
||||||
|
|
||||||
-(BOOL)isUsableInHotPocket;
|
|
||||||
|
|
||||||
@end
|
|
||||||
|
|
||||||
NS_ASSUME_NONNULL_END
|
|
|
@ -1,30 +0,0 @@
|
||||||
//
|
|
||||||
// NSURL+HotPocketExtensions.m
|
|
||||||
// HotPocket (macOS)
|
|
||||||
//
|
|
||||||
// Created by Tomek Wójcik on 30/09/2025.
|
|
||||||
//
|
|
||||||
|
|
||||||
#import "NSURL+HotPocketExtensions.h"
|
|
||||||
|
|
||||||
@implementation NSURL (HotPocketExtensions)
|
|
||||||
|
|
||||||
-(BOOL)isUsableInHotPocket {
|
|
||||||
static NSArray *supportedSchemes = @[@"http", @"https"];
|
|
||||||
|
|
||||||
if (self.baseURL != nil) {
|
|
||||||
return NO;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (self.scheme == nil || [supportedSchemes containsObject:self.scheme] == NO) {
|
|
||||||
return NO;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (self.host == nil || [@"" isEqualToString:self.host] == YES) {
|
|
||||||
return NO;
|
|
||||||
}
|
|
||||||
|
|
||||||
return YES;
|
|
||||||
}
|
|
||||||
|
|
||||||
@end
|
|
20
services/apple/Shared (App)/Resources/Base.lproj/Main.html
Normal file
|
@ -0,0 +1,20 @@
|
||||||
|
<!DOCTYPE html>
|
||||||
|
<html>
|
||||||
|
<head>
|
||||||
|
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
|
||||||
|
<meta http-equiv="Content-Security-Policy" content="default-src 'self'">
|
||||||
|
|
||||||
|
<meta name="viewport" content="width=device-width, initial-scale=1, user-scalable=no">
|
||||||
|
|
||||||
|
<link rel="stylesheet" href="../Style.css">
|
||||||
|
<script src="../Script.js" defer></script>
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
<img src="../icon-mac-384.png" width="128" height="128" alt="HotPocket Icon">
|
||||||
|
<p class="platform-ios">You can turn on Save to Hotpocket Safari extension in Settings.</p>
|
||||||
|
<p class="platform-mac state-unknown">You can turn on Save to Hotpocket extension in Safari Extensions preferences.</p>
|
||||||
|
<p class="platform-mac state-on">Save to Hotpocket extension is currently on. You can turn it off in Safari Extensions preferences.</p>
|
||||||
|
<p class="platform-mac state-off">Save to Hotpocket extension is currently off. You can turn it on in Safari Extensions preferences.</p>
|
||||||
|
<button class="platform-mac open-preferences">Quit and Open Safari Extensions Preferences…</button>
|
||||||
|
</body>
|
||||||
|
</html>
|
24
services/apple/Shared (App)/Resources/Script.js
Normal file
|
@ -0,0 +1,24 @@
|
||||||
|
function show(platform, enabled, useSettingsInsteadOfPreferences) {
|
||||||
|
document.body.classList.add(`platform-${platform}`);
|
||||||
|
|
||||||
|
if (useSettingsInsteadOfPreferences) {
|
||||||
|
document.getElementsByClassName('platform-mac state-on')[0].innerText = "Save to Hotpocket extension is currently on. You can turn it off in the Extensions section of Safari Settings.";
|
||||||
|
document.getElementsByClassName('platform-mac state-off')[0].innerText = "Save to Hotpocket extension is currently off. You can turn it on in the Extensions section of Safari Settings.";
|
||||||
|
document.getElementsByClassName('platform-mac state-unknown')[0].innerText = "You can turn on Save to Hotpocket extension in the Extensions section of Safari Settings.";
|
||||||
|
document.getElementsByClassName('platform-mac open-preferences')[0].innerText = "Quit and Open Safari Settings…";
|
||||||
|
}
|
||||||
|
|
||||||
|
if (typeof enabled === "boolean") {
|
||||||
|
document.body.classList.toggle(`state-on`, enabled);
|
||||||
|
document.body.classList.toggle(`state-off`, !enabled);
|
||||||
|
} else {
|
||||||
|
document.body.classList.remove(`state-on`);
|
||||||
|
document.body.classList.remove(`state-off`);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function openPreferences() {
|
||||||
|
webkit.messageHandlers.controller.postMessage("open-preferences");
|
||||||
|
}
|
||||||
|
|
||||||
|
document.querySelector("button.open-preferences").addEventListener("click", openPreferences);
|
63
services/apple/Shared (App)/Resources/Style.css
Normal file
|
@ -0,0 +1,63 @@
|
||||||
|
* {
|
||||||
|
-webkit-user-select: none;
|
||||||
|
-webkit-user-drag: none;
|
||||||
|
cursor: default;
|
||||||
|
}
|
||||||
|
|
||||||
|
:root {
|
||||||
|
color-scheme: light dark;
|
||||||
|
|
||||||
|
--spacing: 20px;
|
||||||
|
}
|
||||||
|
|
||||||
|
html {
|
||||||
|
height: 100%;
|
||||||
|
}
|
||||||
|
|
||||||
|
body {
|
||||||
|
background: #212529;
|
||||||
|
color: white;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
flex-direction: column;
|
||||||
|
|
||||||
|
gap: var(--spacing);
|
||||||
|
margin: 0 calc(var(--spacing) * 2);
|
||||||
|
height: 100%;
|
||||||
|
|
||||||
|
font: -apple-system-short-body;
|
||||||
|
text-align: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
body:not(.platform-mac, .platform-ios) :is(.platform-mac, .platform-ios) {
|
||||||
|
display: none;
|
||||||
|
}
|
||||||
|
|
||||||
|
body.platform-ios .platform-mac {
|
||||||
|
display: none;
|
||||||
|
}
|
||||||
|
|
||||||
|
body.platform-mac .platform-ios {
|
||||||
|
display: none;
|
||||||
|
}
|
||||||
|
|
||||||
|
body.platform-ios .platform-mac {
|
||||||
|
display: none;
|
||||||
|
}
|
||||||
|
|
||||||
|
body:not(.state-on, .state-off) :is(.state-on, .state-off) {
|
||||||
|
display: none;
|
||||||
|
}
|
||||||
|
|
||||||
|
body.state-on :is(.state-off, .state-unknown) {
|
||||||
|
display: none;
|
||||||
|
}
|
||||||
|
|
||||||
|
body.state-off :is(.state-on, .state-unknown) {
|
||||||
|
display: none;
|
||||||
|
}
|
||||||
|
|
||||||
|
button {
|
||||||
|
font-size: 1em;
|
||||||
|
}
|
Before Width: | Height: | Size: 38 KiB After Width: | Height: | Size: 38 KiB |
26
services/apple/Shared (App)/ViewController.h
Normal file
|
@ -0,0 +1,26 @@
|
||||||
|
//
|
||||||
|
// ViewController.h
|
||||||
|
// Shared (App)
|
||||||
|
//
|
||||||
|
// Created by Tomek Wójcik on 21/08/2025.
|
||||||
|
//
|
||||||
|
|
||||||
|
#import <TargetConditionals.h>
|
||||||
|
|
||||||
|
#if TARGET_OS_IOS
|
||||||
|
|
||||||
|
#import <UIKit/UIKit.h>
|
||||||
|
|
||||||
|
typedef UIViewController PlatformViewController;
|
||||||
|
|
||||||
|
#elif TARGET_OS_OSX
|
||||||
|
|
||||||
|
#import <Cocoa/Cocoa.h>
|
||||||
|
|
||||||
|
typedef NSViewController PlatformViewController;
|
||||||
|
|
||||||
|
#endif
|
||||||
|
|
||||||
|
@interface ViewController : PlatformViewController
|
||||||
|
|
||||||
|
@end
|
76
services/apple/Shared (App)/ViewController.m
Normal file
|
@ -0,0 +1,76 @@
|
||||||
|
//
|
||||||
|
// ViewController.m
|
||||||
|
// Shared (App)
|
||||||
|
//
|
||||||
|
// Created by Tomek Wójcik on 21/08/2025.
|
||||||
|
//
|
||||||
|
|
||||||
|
#import "ViewController.h"
|
||||||
|
|
||||||
|
#import <WebKit/WebKit.h>
|
||||||
|
|
||||||
|
#if TARGET_OS_OSX
|
||||||
|
#import <SafariServices/SafariServices.h>
|
||||||
|
#endif
|
||||||
|
|
||||||
|
static NSString * const extensionBundleIdentifier = @"pl.bthlabs.HotPocket.HotPocket.Extension";
|
||||||
|
|
||||||
|
@interface ViewController () <WKNavigationDelegate, WKScriptMessageHandler>
|
||||||
|
|
||||||
|
@property (nonatomic) IBOutlet WKWebView *webView;
|
||||||
|
|
||||||
|
@end
|
||||||
|
|
||||||
|
@implementation ViewController
|
||||||
|
|
||||||
|
- (void)viewDidLoad {
|
||||||
|
[super viewDidLoad];
|
||||||
|
|
||||||
|
_webView.navigationDelegate = self;
|
||||||
|
|
||||||
|
#if TARGET_OS_IOS
|
||||||
|
_webView.scrollView.scrollEnabled = NO;
|
||||||
|
#endif
|
||||||
|
|
||||||
|
[_webView.configuration.userContentController addScriptMessageHandler:self name:@"controller"];
|
||||||
|
|
||||||
|
[_webView loadFileURL:[NSBundle.mainBundle URLForResource:@"Main" withExtension:@"html"] allowingReadAccessToURL:NSBundle.mainBundle.resourceURL];
|
||||||
|
}
|
||||||
|
|
||||||
|
- (void)webView:(WKWebView *)webView didFinishNavigation:(WKNavigation *)navigation {
|
||||||
|
#if TARGET_OS_IOS
|
||||||
|
[webView evaluateJavaScript:@"show('ios')" completionHandler:nil];
|
||||||
|
#elif TARGET_OS_OSX
|
||||||
|
[webView evaluateJavaScript:@"show('mac')" completionHandler:nil];
|
||||||
|
|
||||||
|
[SFSafariExtensionManager getStateOfSafariExtensionWithIdentifier:extensionBundleIdentifier completionHandler:^(SFSafariExtensionState *state, NSError *error) {
|
||||||
|
dispatch_async(dispatch_get_main_queue(), ^{
|
||||||
|
if (!state) {
|
||||||
|
// Insert code to inform the user something went wrong.
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
NSString *isExtensionEnabledAsString = state.isEnabled ? @"true" : @"false";
|
||||||
|
if (@available(macOS 13, *))
|
||||||
|
[webView evaluateJavaScript:[NSString stringWithFormat:@"show('mac', %@, true)", isExtensionEnabledAsString] completionHandler:nil];
|
||||||
|
else
|
||||||
|
[webView evaluateJavaScript:[NSString stringWithFormat:@"show('mac', %@, false)", isExtensionEnabledAsString] completionHandler:nil];
|
||||||
|
});
|
||||||
|
}];
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
- (void)userContentController:(WKUserContentController *)userContentController didReceiveScriptMessage:(WKScriptMessage *)message {
|
||||||
|
#if TARGET_OS_OSX
|
||||||
|
if (![message.body isEqualToString:@"open-preferences"])
|
||||||
|
return;
|
||||||
|
|
||||||
|
[SFSafariApplication showPreferencesForExtensionWithIdentifier:extensionBundleIdentifier completionHandler:^(NSError *error) {
|
||||||
|
dispatch_async(dispatch_get_main_queue(), ^{
|
||||||
|
[NSApp terminate:self];
|
||||||
|
});
|
||||||
|
}];
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
@end
|
|
@ -1,27 +0,0 @@
|
||||||
//
|
|
||||||
// HPShareExtensionHelper.h
|
|
||||||
// HotPocket
|
|
||||||
//
|
|
||||||
// Created by Tomek Wójcik on 27/09/2025.
|
|
||||||
//
|
|
||||||
|
|
||||||
#import <Foundation/Foundation.h>
|
|
||||||
|
|
||||||
NS_ASSUME_NONNULL_BEGIN
|
|
||||||
|
|
||||||
@class HPSharedItemsContainer;
|
|
||||||
|
|
||||||
typedef void (^HPShareExtensionHelperHandleItemsCompletionHandler)(NSURL * _Nullable url);
|
|
||||||
|
|
||||||
@interface HPShareExtensionHelper : NSObject
|
|
||||||
|
|
||||||
@property NSExtensionContext *context;
|
|
||||||
@property HPSharedItemsContainer *items;
|
|
||||||
|
|
||||||
-(instancetype)initWithContext:(NSExtensionContext *)context;
|
|
||||||
|
|
||||||
-(void)processItems:(HPShareExtensionHelperHandleItemsCompletionHandler)completionHandler;
|
|
||||||
|
|
||||||
@end
|
|
||||||
|
|
||||||
NS_ASSUME_NONNULL_END
|
|
|
@ -1,102 +0,0 @@
|
||||||
//
|
|
||||||
// HPShareExtensionHelper.m
|
|
||||||
// HotPocket
|
|
||||||
//
|
|
||||||
// Created by Tomek Wójcik on 27/09/2025.
|
|
||||||
//
|
|
||||||
|
|
||||||
#import <UniformTypeIdentifiers/UniformTypeIdentifiers.h>
|
|
||||||
|
|
||||||
#import "HPShareExtensionHelper.h"
|
|
||||||
|
|
||||||
#import "HPSharedItem.h"
|
|
||||||
#import "HPSharedItemsContainer.h"
|
|
||||||
|
|
||||||
@implementation HPShareExtensionHelper (HPShareExtensionHelperPrivate)
|
|
||||||
|
|
||||||
@end
|
|
||||||
|
|
||||||
@implementation HPShareExtensionHelper
|
|
||||||
|
|
||||||
-(instancetype)initWithContext:(NSExtensionContext *)context {
|
|
||||||
if (self = [super init]) {
|
|
||||||
self.context = context;
|
|
||||||
self.items = [[HPSharedItemsContainer alloc] init];
|
|
||||||
}
|
|
||||||
|
|
||||||
return self;
|
|
||||||
}
|
|
||||||
|
|
||||||
-(void)processItems:(HPShareExtensionHelperHandleItemsCompletionHandler)completionHandler {
|
|
||||||
// Depending on the app, the URL might be stored in `public.url` attachment or elsewhere.
|
|
||||||
// For example, the YouTube app passes it in `public.plain-text`. Because of course it does.
|
|
||||||
// Furthermore, for some bizarre reason the recommended way of extracting the URL when sharing from a browser
|
|
||||||
// is to run a JS snippet and examine its output.
|
|
||||||
// This method will iterate through all the shared items and their attachments and attempt to extract
|
|
||||||
// the URL candidates.
|
|
||||||
//
|
|
||||||
// Also note that handler for `public.url` explicitly requests the payload to be corced to `NSURL *`. Leaving it
|
|
||||||
// at `NSData *` would cause iOS to, wait for it!, fetch the URL and dump the response body in the payload :D.
|
|
||||||
//
|
|
||||||
// This is so _so_ *so* dumb. But hey, at least I learned how to to "chords" in CGD ¯\_(ツ)_/¯
|
|
||||||
UTType *propertyListType = [UTType typeWithFilenameExtension:@"plist"];
|
|
||||||
|
|
||||||
dispatch_group_t dispatchGroup = dispatch_group_create();
|
|
||||||
dispatch_queue_t queue = dispatch_queue_create("HPShareExtensionHelper.processItems.queue", DISPATCH_QUEUE_SERIAL);
|
|
||||||
|
|
||||||
for (NSExtensionItem *inputItem in self.context.inputItems) {
|
|
||||||
#ifdef DEBUG
|
|
||||||
NSLog(@"-[HPShareExtensionHelper processItems:] inputItem.userInfo=`%@`", inputItem);
|
|
||||||
#endif
|
|
||||||
[inputItem.attachments enumerateObjectsUsingBlock:^(NSItemProvider *attachment, NSUInteger index, BOOL *stop) {
|
|
||||||
dispatch_group_enter(dispatchGroup);
|
|
||||||
|
|
||||||
if ([attachment hasItemConformingToTypeIdentifier:propertyListType.identifier] == YES) {
|
|
||||||
[attachment loadItemForTypeIdentifier:propertyListType.identifier
|
|
||||||
options:nil
|
|
||||||
completionHandler:^(NSDictionary *payload, NSError *error) {
|
|
||||||
dispatch_async(queue, ^{
|
|
||||||
self.items.primaryItem = [[HPSharedItem alloc] initWithPayload:payload
|
|
||||||
typeIdentifier:propertyListType.identifier
|
|
||||||
error:error];
|
|
||||||
|
|
||||||
dispatch_group_leave(dispatchGroup);
|
|
||||||
});
|
|
||||||
}];
|
|
||||||
} else if ([attachment hasItemConformingToTypeIdentifier:@"public.url"] == YES) {
|
|
||||||
[attachment loadItemForTypeIdentifier:@"public.url"
|
|
||||||
options:nil
|
|
||||||
completionHandler:^(NSURL *payload, NSError *error) {
|
|
||||||
dispatch_async(queue, ^{
|
|
||||||
[self.items.candidateItems addObject:[[HPSharedItem alloc] initWithPayload:payload
|
|
||||||
typeIdentifier:@"public.url"
|
|
||||||
error:error]];
|
|
||||||
|
|
||||||
dispatch_group_leave(dispatchGroup);
|
|
||||||
});
|
|
||||||
}];
|
|
||||||
} else if ([attachment hasItemConformingToTypeIdentifier:@"public.plain-text"] == YES) {
|
|
||||||
[attachment loadItemForTypeIdentifier:@"public.plain-text"
|
|
||||||
options:nil
|
|
||||||
completionHandler:^(NSString *payload, NSError *error) {
|
|
||||||
dispatch_async(queue, ^{
|
|
||||||
[self.items.candidateItems addObject:[[HPSharedItem alloc] initWithPayload:payload
|
|
||||||
typeIdentifier:@"public.plain-text"
|
|
||||||
error:error]];
|
|
||||||
|
|
||||||
dispatch_group_leave(dispatchGroup);
|
|
||||||
});
|
|
||||||
}];
|
|
||||||
} else {
|
|
||||||
dispatch_group_leave(dispatchGroup);
|
|
||||||
}
|
|
||||||
}];
|
|
||||||
|
|
||||||
dispatch_group_notify(dispatchGroup, dispatch_get_main_queue(), ^{
|
|
||||||
NSURL *result = [self.items resolveURL];
|
|
||||||
completionHandler(result);
|
|
||||||
});
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@end
|
|
|
@ -1,24 +0,0 @@
|
||||||
//
|
|
||||||
// HPSharedItem.h
|
|
||||||
// HotPocket
|
|
||||||
//
|
|
||||||
// Created by Tomek Wójcik on 27/09/2025.
|
|
||||||
//
|
|
||||||
|
|
||||||
#import <Foundation/Foundation.h>
|
|
||||||
|
|
||||||
NS_ASSUME_NONNULL_BEGIN
|
|
||||||
|
|
||||||
@interface HPSharedItem : NSObject
|
|
||||||
|
|
||||||
@property (nullable) id payload;
|
|
||||||
@property NSString *typeIdentifier;
|
|
||||||
@property (nullable) NSError *error;
|
|
||||||
|
|
||||||
-(instancetype)initWithPayload:(nullable id)payload typeIdentifier:(NSString *)typeIdentifier error:(nullable NSError *)error;
|
|
||||||
|
|
||||||
-(NSURL *)maybeURL;
|
|
||||||
|
|
||||||
@end
|
|
||||||
|
|
||||||
NS_ASSUME_NONNULL_END
|
|
|
@ -1,47 +0,0 @@
|
||||||
//
|
|
||||||
// HPSharedItem.m
|
|
||||||
// HotPocket
|
|
||||||
//
|
|
||||||
// Created by Tomek Wójcik on 27/09/2025.
|
|
||||||
//
|
|
||||||
|
|
||||||
#import <UniformTypeIdentifiers/UniformTypeIdentifiers.h>
|
|
||||||
|
|
||||||
#import "HPSharedItem.h"
|
|
||||||
|
|
||||||
@implementation HPSharedItem
|
|
||||||
|
|
||||||
-(instancetype)initWithPayload:(id)payload typeIdentifier:(NSString *)typeIdentifier error:(NSError *)error {
|
|
||||||
if (self = [super init]) {
|
|
||||||
self.payload = payload;
|
|
||||||
self.typeIdentifier = typeIdentifier;
|
|
||||||
self.error = error;
|
|
||||||
}
|
|
||||||
|
|
||||||
return self;
|
|
||||||
}
|
|
||||||
|
|
||||||
-(NSURL *)maybeURL {
|
|
||||||
if (self.error != nil) {
|
|
||||||
return nil;
|
|
||||||
}
|
|
||||||
|
|
||||||
if ([self.typeIdentifier isEqualToString:[UTType typeWithFilenameExtension:@"plist"].identifier] == YES) {
|
|
||||||
NSDictionary *propertyList = self.payload;
|
|
||||||
NSDictionary *jsHelperResult = [propertyList valueForKey:NSExtensionJavaScriptPreprocessingResultsKey];
|
|
||||||
|
|
||||||
if ([jsHelperResult valueForKey:@"iHateComputers"] == nil) {
|
|
||||||
return nil;
|
|
||||||
}
|
|
||||||
|
|
||||||
return [NSURL URLWithString:[jsHelperResult valueForKey:@"url"]];
|
|
||||||
} else if ([self.typeIdentifier isEqualToString:@"public.url"] == YES) {
|
|
||||||
return self.payload;
|
|
||||||
} if ([self.typeIdentifier isEqualToString:@"public.plain-text"] == YES) {
|
|
||||||
return [NSURL URLWithString:self.payload];
|
|
||||||
}
|
|
||||||
|
|
||||||
return nil;
|
|
||||||
}
|
|
||||||
|
|
||||||
@end
|
|
|
@ -1,23 +0,0 @@
|
||||||
//
|
|
||||||
// HPSharedItemsContainer.h
|
|
||||||
// HotPocket
|
|
||||||
//
|
|
||||||
// Created by Tomek Wójcik on 27/09/2025.
|
|
||||||
//
|
|
||||||
|
|
||||||
#import <Foundation/Foundation.h>
|
|
||||||
|
|
||||||
NS_ASSUME_NONNULL_BEGIN
|
|
||||||
|
|
||||||
@class HPSharedItem;
|
|
||||||
|
|
||||||
@interface HPSharedItemsContainer : NSObject
|
|
||||||
|
|
||||||
@property (nullable) HPSharedItem *primaryItem;
|
|
||||||
@property NSMutableArray<HPSharedItem *> *candidateItems;
|
|
||||||
|
|
||||||
-(NSURL *)resolveURL;
|
|
||||||
|
|
||||||
@end
|
|
||||||
|
|
||||||
NS_ASSUME_NONNULL_END
|
|
|
@ -1,63 +0,0 @@
|
||||||
//
|
|
||||||
// HPSharedItemsContainer.m
|
|
||||||
// HotPocket
|
|
||||||
//
|
|
||||||
// Created by Tomek Wójcik on 27/09/2025.
|
|
||||||
//
|
|
||||||
|
|
||||||
#import "HPSharedItemsContainer.h"
|
|
||||||
|
|
||||||
#import "HPSharedItem.h"
|
|
||||||
#import "NSURL+HotPocketExtensions.h"
|
|
||||||
|
|
||||||
@implementation HPSharedItemsContainer (HPSharedItemsContainerPrivate)
|
|
||||||
|
|
||||||
-(NSURL *)validatedURL:(NSURL *)url {
|
|
||||||
if (url.isUsableInHotPocket == NO) {
|
|
||||||
return nil;
|
|
||||||
}
|
|
||||||
|
|
||||||
return url;
|
|
||||||
}
|
|
||||||
|
|
||||||
@end
|
|
||||||
|
|
||||||
@implementation HPSharedItemsContainer
|
|
||||||
|
|
||||||
-(instancetype)init {
|
|
||||||
if (self = [super init]) {
|
|
||||||
self.primaryItem = nil;
|
|
||||||
self.candidateItems = [[NSMutableArray alloc] initWithCapacity:1];
|
|
||||||
}
|
|
||||||
|
|
||||||
return self;
|
|
||||||
}
|
|
||||||
|
|
||||||
-(NSURL *)resolveURL {
|
|
||||||
NSURL *result = nil;
|
|
||||||
|
|
||||||
if (self.primaryItem != nil) {
|
|
||||||
result = [self validatedURL:[self.primaryItem maybeURL]];
|
|
||||||
}
|
|
||||||
|
|
||||||
if ([self.candidateItems count] > 0) {
|
|
||||||
NSUInteger itemCandidateIndex = 0;
|
|
||||||
while (result == nil) {
|
|
||||||
HPSharedItem *itemCandidate = [self.candidateItems objectAtIndex:itemCandidateIndex];
|
|
||||||
|
|
||||||
result = [self validatedURL:itemCandidate.maybeURL];
|
|
||||||
if (result != nil) {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
itemCandidateIndex += 1;
|
|
||||||
if (itemCandidateIndex >= [self.candidateItems count]) {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
@end
|
|
|
@ -1,23 +0,0 @@
|
||||||
services:
|
|
||||||
apple-ci:
|
|
||||||
build:
|
|
||||||
context: ".."
|
|
||||||
dockerfile: "apple/Dockerfile"
|
|
||||||
target: "development"
|
|
||||||
image: "docker-hosted.nexus.bthlabs.pl/hotpocket/apple:ci-local"
|
|
||||||
command: "echo 'NOOP'"
|
|
||||||
environment:
|
|
||||||
PYTHONBREAKPOINT: "ipdb.set_trace"
|
|
||||||
HOTPOCKET_PACKAGES_ENV: "${HOTPOCKET_EXTENSION_ENV:-docker}"
|
|
||||||
# REQUESTS_CA_BUNDLE: "/srv/tls/requests_ca_bundle.pem"
|
|
||||||
RUN_POETRY_INSTALL: "true"
|
|
||||||
RUN_YARN_INSTALL: "false"
|
|
||||||
SETUP_BACKEND: "true"
|
|
||||||
SETUP_FRONTEND: "false"
|
|
||||||
volumes:
|
|
||||||
- "apple_venv:/srv/venv"
|
|
||||||
- "apple_node_modules:/srv/node_modules"
|
|
||||||
- "../tls:/srv/tls"
|
|
||||||
restart: "no"
|
|
||||||
stdin_open: true
|
|
||||||
tty: true
|
|
|
@ -1,29 +0,0 @@
|
||||||
services:
|
|
||||||
apple-management:
|
|
||||||
build:
|
|
||||||
context: ".."
|
|
||||||
dockerfile: "apple/Dockerfile"
|
|
||||||
target: "development"
|
|
||||||
image: "docker-hosted.nexus.bthlabs.pl/hotpocket/apple:local"
|
|
||||||
command: "echo 'NOOP'"
|
|
||||||
environment: &apple-env
|
|
||||||
PYTHONBREAKPOINT: "ipdb.set_trace"
|
|
||||||
HOTPOCKET_EXTENSION_ENV: "${HOTPOCKET_EXTENSION_ENV:-docker}"
|
|
||||||
REQUESTS_CA_BUNDLE: "/srv/tls/requests_ca_bundle.pem"
|
|
||||||
RUN_POETRY_INSTALL: "true"
|
|
||||||
RUN_YARN_INSTALL: "false"
|
|
||||||
SETUP_BACKEND: "true"
|
|
||||||
SETUP_FRONTEND: "false"
|
|
||||||
volumes:
|
|
||||||
- "apple_venv:/srv/venv"
|
|
||||||
- "apple_node_modules:/srv/node_modules"
|
|
||||||
- ".:/srv/app"
|
|
||||||
- "../packages:/srv/packages"
|
|
||||||
- "../tls:/srv/tls"
|
|
||||||
restart: "no"
|
|
||||||
stdin_open: true
|
|
||||||
tty: true
|
|
||||||
|
|
||||||
volumes:
|
|
||||||
apple_venv:
|
|
||||||
apple_node_modules:
|
|
|
@ -7,10 +7,6 @@
|
||||||
|
|
||||||
#import <UIKit/UIKit.h>
|
#import <UIKit/UIKit.h>
|
||||||
|
|
||||||
@class HPAuthFlow;
|
|
||||||
|
|
||||||
@interface AppDelegate : UIResponder <UIApplicationDelegate>
|
@interface AppDelegate : UIResponder <UIApplicationDelegate>
|
||||||
|
|
||||||
@property (strong, nonnull) HPAuthFlow *authFlow;
|
|
||||||
|
|
||||||
@end
|
@end
|
||||||
|
|
|
@ -7,13 +7,10 @@
|
||||||
|
|
||||||
#import "AppDelegate.h"
|
#import "AppDelegate.h"
|
||||||
|
|
||||||
#import "HPAuthFlow.h"
|
|
||||||
|
|
||||||
@implementation AppDelegate
|
@implementation AppDelegate
|
||||||
|
|
||||||
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
|
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
|
||||||
self.authFlow = [[HPAuthFlow alloc] init];
|
// Override point for customization after application launch.
|
||||||
|
|
||||||
return YES;
|
return YES;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -1,18 +0,0 @@
|
||||||
//
|
|
||||||
// AuthorizationProgressViewController.h
|
|
||||||
// HotPocket (iOS)
|
|
||||||
//
|
|
||||||
// Created by Tomek Wójcik on 25/09/2025.
|
|
||||||
//
|
|
||||||
|
|
||||||
#import <UIKit/UIKit.h>
|
|
||||||
|
|
||||||
NS_ASSUME_NONNULL_BEGIN
|
|
||||||
|
|
||||||
@interface AuthorizationProgressViewController : UIViewController
|
|
||||||
|
|
||||||
@property IBOutlet UIActivityIndicatorView *progressIndicator;
|
|
||||||
|
|
||||||
@end
|
|
||||||
|
|
||||||
NS_ASSUME_NONNULL_END
|
|
|
@ -1,74 +0,0 @@
|
||||||
//
|
|
||||||
// AuthorizationProgressViewController.m
|
|
||||||
// HotPocket (iOS)
|
|
||||||
//
|
|
||||||
// Created by Tomek Wójcik on 25/09/2025.
|
|
||||||
//
|
|
||||||
|
|
||||||
#import "AuthorizationProgressViewController.h"
|
|
||||||
|
|
||||||
#import "AppDelegate.h"
|
|
||||||
#import "HPCredentialsHelper.h"
|
|
||||||
|
|
||||||
@interface AuthorizationProgressViewController (AuthorizationProgressViewControllerPrivate)
|
|
||||||
|
|
||||||
#pragma mark - Private interface
|
|
||||||
|
|
||||||
@end
|
|
||||||
|
|
||||||
@implementation AuthorizationProgressViewController
|
|
||||||
|
|
||||||
#pragma mark - View lifecycle
|
|
||||||
|
|
||||||
-(void)viewDidLoad {
|
|
||||||
[super viewDidLoad];
|
|
||||||
}
|
|
||||||
|
|
||||||
-(void)viewWillAppear:(BOOL)animated {
|
|
||||||
[super viewWillAppear:animated];
|
|
||||||
[self.progressIndicator startAnimating];
|
|
||||||
|
|
||||||
AppDelegate *appDelegate = [[UIApplication sharedApplication] delegate];
|
|
||||||
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(onAuthFlowDidFinish:) name:@"AuthFlowDidFinish" object:appDelegate.authFlow];
|
|
||||||
}
|
|
||||||
|
|
||||||
-(void)viewWillDisappear:(BOOL)animated {
|
|
||||||
[super viewWillDisappear:animated];
|
|
||||||
[[NSNotificationCenter defaultCenter] removeObserver:self];
|
|
||||||
}
|
|
||||||
|
|
||||||
-(void)viewDidDisappear:(BOOL)animated {
|
|
||||||
[super viewDidDisappear:animated];
|
|
||||||
[self.progressIndicator stopAnimating];
|
|
||||||
}
|
|
||||||
|
|
||||||
#pragma mark - Notification handlers
|
|
||||||
|
|
||||||
-(void)onAuthFlowDidFinish:(NSNotification *)notification {
|
|
||||||
dispatch_async(dispatch_get_main_queue(), ^{
|
|
||||||
#ifdef DEBUG
|
|
||||||
NSLog(@"-[AuthorizationViewController onAuthFlowDidFinish:] notification=`%@`", notification);
|
|
||||||
#endif
|
|
||||||
HPCredentials *credentials = [[HPCredentialsHelper sharedHelper] getCredentials];
|
|
||||||
|
|
||||||
if (credentials.usable == NO) {
|
|
||||||
UIAlertController *alert = [UIAlertController alertControllerWithTitle:NSLocalizedString(@"Oops!", @"Oops!")
|
|
||||||
message:NSLocalizedString(@"HotPocket couldn't complete this operation.", @"HotPocket couldn't complete this operation.")
|
|
||||||
preferredStyle:UIAlertControllerStyleAlert];
|
|
||||||
|
|
||||||
[alert addAction:[UIAlertAction actionWithTitle:NSLocalizedString(@"Oh well", @"Oh well")
|
|
||||||
style:UIAlertActionStyleDefault
|
|
||||||
handler:^(UIAlertAction *action) {
|
|
||||||
[alert dismissViewControllerAnimated:YES completion:^{
|
|
||||||
[self.navigationController popViewControllerAnimated:YES];
|
|
||||||
}];
|
|
||||||
}]];
|
|
||||||
|
|
||||||
[self presentViewController:alert animated:YES completion:nil];
|
|
||||||
} else {
|
|
||||||
[self.navigationController popToRootViewControllerAnimated:YES];
|
|
||||||
}
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
@end
|
|
|
@ -1,22 +0,0 @@
|
||||||
//
|
|
||||||
// AuthorizationViewController.h
|
|
||||||
// HotPocket (iOS)
|
|
||||||
//
|
|
||||||
// Created by Tomek Wójcik on 25/09/2025.
|
|
||||||
//
|
|
||||||
|
|
||||||
#import <UIKit/UIKit.h>
|
|
||||||
|
|
||||||
NS_ASSUME_NONNULL_BEGIN
|
|
||||||
|
|
||||||
@interface AuthorizationViewController : UIViewController
|
|
||||||
|
|
||||||
@property UIImageView *invalidURLWarningView;
|
|
||||||
|
|
||||||
@property IBOutlet UITextField *instanceURLField;
|
|
||||||
|
|
||||||
-(IBAction)doStartAuthorizationFlow:(id)sender;
|
|
||||||
|
|
||||||
@end
|
|
||||||
|
|
||||||
NS_ASSUME_NONNULL_END
|
|
|
@ -1,104 +0,0 @@
|
||||||
//
|
|
||||||
// AuthorizationViewController.m
|
|
||||||
// HotPocket (iOS)
|
|
||||||
//
|
|
||||||
// Created by Tomek Wójcik on 25/09/2025.
|
|
||||||
//
|
|
||||||
|
|
||||||
#import "AuthorizationViewController.h"
|
|
||||||
|
|
||||||
#import "AppDelegate.h"
|
|
||||||
#import "AuthorizationProgressViewController.h"
|
|
||||||
#import "HPAuthFlow.h"
|
|
||||||
#import "HPCredentialsHelper.h"
|
|
||||||
#import "MainViewController.h"
|
|
||||||
#import "NSURL+HotPocketExtensions.h"
|
|
||||||
|
|
||||||
@interface AuthorizationViewController (AuthorizationViewControllerPrivate)
|
|
||||||
|
|
||||||
#pragma mark - Private interface
|
|
||||||
|
|
||||||
@end
|
|
||||||
|
|
||||||
@implementation AuthorizationViewController
|
|
||||||
|
|
||||||
#pragma mark - View lifecycle
|
|
||||||
|
|
||||||
-(void)viewDidLoad {
|
|
||||||
[super viewDidLoad];
|
|
||||||
|
|
||||||
self.invalidURLWarningView = [[UIImageView alloc] initWithImage:[UIImage systemImageNamed:@"exclamationmark.circle.fill"]];
|
|
||||||
self.invalidURLWarningView.contentMode = UIViewContentModeScaleAspectFit;
|
|
||||||
self.invalidURLWarningView.frame = CGRectMake(0, 0, 16, 16);
|
|
||||||
self.invalidURLWarningView.tintColor = [UIColor colorNamed:@"WarningColor"];
|
|
||||||
}
|
|
||||||
|
|
||||||
-(void)viewWillAppear:(BOOL)animated {
|
|
||||||
[super viewWillAppear:animated];
|
|
||||||
|
|
||||||
self.instanceURLField.rightView = self.invalidURLWarningView;
|
|
||||||
self.instanceURLField.rightViewMode = UITextFieldViewModeNever;
|
|
||||||
|
|
||||||
[self.instanceURLField addTarget:self action:@selector(onInstanceURLFieldChanged:) forControlEvents:UIControlEventEditingChanged];
|
|
||||||
}
|
|
||||||
|
|
||||||
#pragma mark - Actions
|
|
||||||
|
|
||||||
-(IBAction)doStartAuthorizationFlow:(id)sender {
|
|
||||||
#ifdef DEBUG
|
|
||||||
NSLog(@"-[AuthorizationViewController doStartAuthorizationFlow:] instanceURL=`%@`", self.instanceURLField.text);
|
|
||||||
#endif
|
|
||||||
if (!self.instanceURLField.text) {
|
|
||||||
// ???
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
NSURL *instanceURL = [NSURL URLWithString:self.instanceURLField.text];
|
|
||||||
if (instanceURL.isUsableInHotPocket == NO) {
|
|
||||||
// ???
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
UIApplication *application = [UIApplication sharedApplication];
|
|
||||||
AppDelegate *appDeleate = [application delegate];
|
|
||||||
appDeleate.authFlow.baseURL = instanceURL;
|
|
||||||
|
|
||||||
NSURL *authURL = [appDeleate.authFlow start];
|
|
||||||
if (authURL == nil) {
|
|
||||||
// ???
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if ([application canOpenURL:authURL] == YES) {
|
|
||||||
[application openURL:authURL options:@{} completionHandler:^(BOOL result) {
|
|
||||||
if (result == YES) {
|
|
||||||
AuthorizationProgressViewController *authorizationProgressViewController = [self.storyboard instantiateViewControllerWithIdentifier:@"AuthorizationProgressViewController"];
|
|
||||||
[self.navigationController pushViewController:authorizationProgressViewController animated:YES];
|
|
||||||
}
|
|
||||||
}];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
#pragma mark - Event handlers
|
|
||||||
|
|
||||||
-(void)onInstanceURLFieldChanged:(UITextField *)sender {
|
|
||||||
sender.rightViewMode = UITextFieldViewModeNever;
|
|
||||||
|
|
||||||
if (!sender.text || [@"" isEqualToString:sender.text]) {
|
|
||||||
sender.rightViewMode = UITextFieldViewModeAlways;
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
NSURL *url = [NSURL URLWithString:sender.text];
|
|
||||||
if (url == nil) {
|
|
||||||
sender.rightViewMode = UITextFieldViewModeAlways;
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (url.isUsableInHotPocket == NO) {
|
|
||||||
sender.rightViewMode = UITextFieldViewModeAlways;
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@end
|
|
|
@ -1,8 +1,8 @@
|
||||||
<?xml version="1.0" encoding="UTF-8"?>
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
<document type="com.apple.InterfaceBuilder3.CocoaTouch.Storyboard.XIB" version="3.0" toolsVersion="24127" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" launchScreen="YES" useTraitCollections="YES" useSafeAreas="YES" colorMatched="YES" initialViewController="01J-lp-oVM">
|
<document type="com.apple.InterfaceBuilder3.CocoaTouch.Storyboard.XIB" version="3.0" toolsVersion="23727" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" launchScreen="YES" useTraitCollections="YES" useSafeAreas="YES" colorMatched="YES" initialViewController="01J-lp-oVM">
|
||||||
<device id="retina6_12" orientation="portrait" appearance="light"/>
|
<device id="retina6_12" orientation="portrait" appearance="light"/>
|
||||||
<dependencies>
|
<dependencies>
|
||||||
<plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="24063"/>
|
<plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="23721"/>
|
||||||
<capability name="Image references" minToolsVersion="12.0"/>
|
<capability name="Image references" minToolsVersion="12.0"/>
|
||||||
<capability name="Named colors" minToolsVersion="9.0"/>
|
<capability name="Named colors" minToolsVersion="9.0"/>
|
||||||
<capability name="Safe area layout guides" minToolsVersion="9.0"/>
|
<capability name="Safe area layout guides" minToolsVersion="9.0"/>
|
||||||
|
@ -16,25 +16,12 @@
|
||||||
<view key="view" contentMode="scaleToFill" id="Ze5-6b-2t3">
|
<view key="view" contentMode="scaleToFill" id="Ze5-6b-2t3">
|
||||||
<rect key="frame" x="0.0" y="0.0" width="393" height="852"/>
|
<rect key="frame" x="0.0" y="0.0" width="393" height="852"/>
|
||||||
<autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
|
<autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
|
||||||
<subviews>
|
|
||||||
<view contentMode="scaleToFill" fixedFrame="YES" translatesAutoresizingMaskIntoConstraints="NO" id="H2q-Qq-Nf1">
|
|
||||||
<rect key="frame" x="16" y="344" width="361" height="165"/>
|
|
||||||
<autoresizingMask key="autoresizingMask" widthSizable="YES" flexibleMinY="YES" flexibleMaxY="YES"/>
|
|
||||||
<subviews>
|
<subviews>
|
||||||
<imageView clipsSubviews="YES" userInteractionEnabled="NO" contentMode="scaleToFill" horizontalHuggingPriority="251" verticalHuggingPriority="251" fixedFrame="YES" translatesAutoresizingMaskIntoConstraints="NO" id="6HG-Um-bch">
|
<imageView clipsSubviews="YES" userInteractionEnabled="NO" contentMode="scaleToFill" horizontalHuggingPriority="251" verticalHuggingPriority="251" fixedFrame="YES" translatesAutoresizingMaskIntoConstraints="NO" id="6HG-Um-bch">
|
||||||
<rect key="frame" x="116" y="0.0" width="128" height="128"/>
|
<rect key="frame" x="131" y="363" width="128" height="128"/>
|
||||||
<autoresizingMask key="autoresizingMask" flexibleMinX="YES" flexibleMaxX="YES" flexibleMaxY="YES"/>
|
<autoresizingMask key="autoresizingMask" flexibleMinX="YES" flexibleMaxX="YES" flexibleMinY="YES" flexibleMaxY="YES"/>
|
||||||
<imageReference key="image" image="icon-mac-384.png"/>
|
<imageReference key="image" image="LargeIcon"/>
|
||||||
</imageView>
|
</imageView>
|
||||||
<label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" fixedFrame="YES" text="HotPocket by BTHLabs" textAlignment="center" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="v6f-dw-6WO">
|
|
||||||
<rect key="frame" x="0.0" y="136" width="361" height="29"/>
|
|
||||||
<autoresizingMask key="autoresizingMask" widthSizable="YES" flexibleMaxY="YES"/>
|
|
||||||
<fontDescription key="fontDescription" type="system" pointSize="24"/>
|
|
||||||
<color key="textColor" white="1" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
|
|
||||||
<nil key="highlightedColor"/>
|
|
||||||
</label>
|
|
||||||
</subviews>
|
|
||||||
</view>
|
|
||||||
</subviews>
|
</subviews>
|
||||||
<viewLayoutGuide key="safeArea" id="6Tk-OE-BBY"/>
|
<viewLayoutGuide key="safeArea" id="6Tk-OE-BBY"/>
|
||||||
<color key="backgroundColor" name="BackgroundColor"/>
|
<color key="backgroundColor" name="BackgroundColor"/>
|
||||||
|
@ -42,11 +29,11 @@
|
||||||
</viewController>
|
</viewController>
|
||||||
<placeholder placeholderIdentifier="IBFirstResponder" id="iYj-Kq-Ea1" userLabel="First Responder" sceneMemberID="firstResponder"/>
|
<placeholder placeholderIdentifier="IBFirstResponder" id="iYj-Kq-Ea1" userLabel="First Responder" sceneMemberID="firstResponder"/>
|
||||||
</objects>
|
</objects>
|
||||||
<point key="canvasLocation" x="52.671755725190835" y="374.64788732394368"/>
|
<point key="canvasLocation" x="53" y="375"/>
|
||||||
</scene>
|
</scene>
|
||||||
</scenes>
|
</scenes>
|
||||||
<resources>
|
<resources>
|
||||||
<image name="icon-mac-384.png" width="384" height="384"/>
|
<image name="LargeIcon" width="128" height="128"/>
|
||||||
<namedColor name="BackgroundColor">
|
<namedColor name="BackgroundColor">
|
||||||
<color red="0.12941176470588237" green="0.14509803921568629" blue="0.16078431372549021" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
|
<color red="0.12941176470588237" green="0.14509803921568629" blue="0.16078431372549021" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
|
||||||
</namedColor>
|
</namedColor>
|
||||||
|
|
|
@ -1,252 +1,46 @@
|
||||||
<?xml version="1.0" encoding="UTF-8"?>
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
<document type="com.apple.InterfaceBuilder3.CocoaTouch.Storyboard.XIB" version="3.0" toolsVersion="24127" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" useSafeAreas="YES" colorMatched="YES" initialViewController="7Sa-RR-xgc">
|
<document type="com.apple.InterfaceBuilder3.CocoaTouch.Storyboard.XIB" version="3.0" toolsVersion="23727" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" useSafeAreas="YES" colorMatched="YES" initialViewController="BYZ-38-t0r">
|
||||||
<device id="retina6_1" orientation="portrait" appearance="light"/>
|
<device id="retina6_1" orientation="portrait" appearance="light"/>
|
||||||
<dependencies>
|
<dependencies>
|
||||||
<plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="24063"/>
|
<plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="23721"/>
|
||||||
<capability name="Image references" minToolsVersion="12.0"/>
|
|
||||||
<capability name="Named colors" minToolsVersion="9.0"/>
|
<capability name="Named colors" minToolsVersion="9.0"/>
|
||||||
<capability name="Safe area layout guides" minToolsVersion="9.0"/>
|
<capability name="Safe area layout guides" minToolsVersion="9.0"/>
|
||||||
<capability name="documents saved in the Xcode 8 format" minToolsVersion="8.0"/>
|
<capability name="documents saved in the Xcode 8 format" minToolsVersion="8.0"/>
|
||||||
</dependencies>
|
</dependencies>
|
||||||
<scenes>
|
<scenes>
|
||||||
<!--Main View Controller-->
|
<!--View Controller-->
|
||||||
<scene sceneID="tne-QT-ifu">
|
<scene sceneID="tne-QT-ifu">
|
||||||
<objects>
|
<objects>
|
||||||
<viewController storyboardIdentifier="MainViewController" id="BYZ-38-t0r" customClass="MainViewController" sceneMemberID="viewController">
|
<viewController id="BYZ-38-t0r" customClass="ViewController" sceneMemberID="viewController">
|
||||||
<view key="view" contentMode="scaleToFill" id="8bC-Xf-vdC">
|
<view key="view" contentMode="scaleToFill" id="8bC-Xf-vdC">
|
||||||
<rect key="frame" x="0.0" y="0.0" width="414" height="896"/>
|
<rect key="frame" x="0.0" y="0.0" width="414" height="896"/>
|
||||||
<autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
|
<autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
|
||||||
<subviews>
|
<subviews>
|
||||||
<view contentMode="scaleToFill" fixedFrame="YES" translatesAutoresizingMaskIntoConstraints="NO" id="Tdb-RK-EKV">
|
<wkWebView contentMode="scaleToFill" fixedFrame="YES" translatesAutoresizingMaskIntoConstraints="NO" id="RDB-ib-igF">
|
||||||
<rect key="frame" x="20" y="96" width="374" height="165"/>
|
<rect key="frame" x="0.0" y="0.0" width="414" height="896"/>
|
||||||
<autoresizingMask key="autoresizingMask" widthSizable="YES" flexibleMinY="YES" flexibleMaxY="YES"/>
|
<autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
|
||||||
<subviews>
|
<color key="backgroundColor" name="BackgroundColor"/>
|
||||||
<imageView clipsSubviews="YES" userInteractionEnabled="NO" contentMode="scaleToFill" horizontalHuggingPriority="251" verticalHuggingPriority="251" fixedFrame="YES" translatesAutoresizingMaskIntoConstraints="NO" id="57V-kg-4Nx">
|
<wkWebViewConfiguration key="configuration">
|
||||||
<rect key="frame" x="122" y="0.0" width="128" height="128"/>
|
<audiovisualMediaTypes key="mediaTypesRequiringUserActionForPlayback" none="YES"/>
|
||||||
<autoresizingMask key="autoresizingMask" flexibleMinX="YES" flexibleMaxX="YES" flexibleMaxY="YES"/>
|
<wkPreferences key="preferences"/>
|
||||||
<imageReference key="image" image="icon-mac-384.png"/>
|
</wkWebViewConfiguration>
|
||||||
</imageView>
|
</wkWebView>
|
||||||
<label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" fixedFrame="YES" text="HotPocket by BTHLabs" textAlignment="center" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="cP6-uT-Hh4">
|
|
||||||
<rect key="frame" x="0.0" y="136" width="374" height="29"/>
|
|
||||||
<autoresizingMask key="autoresizingMask" widthSizable="YES" flexibleMaxY="YES"/>
|
|
||||||
<fontDescription key="fontDescription" type="system" pointSize="24"/>
|
|
||||||
<color key="textColor" white="1" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
|
|
||||||
<nil key="highlightedColor"/>
|
|
||||||
</label>
|
|
||||||
</subviews>
|
|
||||||
</view>
|
|
||||||
<label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" fixedFrame="YES" text="Safari and Share Extensions are installed." textAlignment="natural" lineBreakMode="wordWrap" numberOfLines="0" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="ltc-Em-W9y" customClass="MultilineLabel">
|
|
||||||
<rect key="frame" x="20" y="306" width="374" height="42"/>
|
|
||||||
<autoresizingMask key="autoresizingMask" widthSizable="YES" flexibleMaxY="YES"/>
|
|
||||||
<fontDescription key="fontDescription" type="system" pointSize="17"/>
|
|
||||||
<color key="textColor" white="1" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
|
|
||||||
<nil key="highlightedColor"/>
|
|
||||||
</label>
|
|
||||||
<label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" fixedFrame="YES" text="Instance URL" textAlignment="natural" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="GYw-2b-qGS">
|
|
||||||
<rect key="frame" x="20" y="356" width="374" height="21"/>
|
|
||||||
<autoresizingMask key="autoresizingMask" widthSizable="YES" flexibleMaxY="YES"/>
|
|
||||||
<fontDescription key="fontDescription" type="system" pointSize="17"/>
|
|
||||||
<color key="textColor" white="1" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
|
|
||||||
<nil key="highlightedColor"/>
|
|
||||||
</label>
|
|
||||||
<button opaque="NO" contentMode="scaleToFill" fixedFrame="YES" contentHorizontalAlignment="leading" contentVerticalAlignment="center" lineBreakMode="middleTruncation" translatesAutoresizingMaskIntoConstraints="NO" id="OPO-AY-zgd">
|
|
||||||
<rect key="frame" x="20" y="385" width="374" height="35"/>
|
|
||||||
<autoresizingMask key="autoresizingMask" widthSizable="YES" flexibleMaxY="YES"/>
|
|
||||||
<inset key="imageEdgeInsets" minX="0.0" minY="0.0" maxX="2.2250738585072014e-308" maxY="0.0"/>
|
|
||||||
<buttonConfiguration key="configuration" style="gray" title="DO NOT LOCALIZE">
|
|
||||||
<color key="baseForegroundColor" name="SecondaryColor"/>
|
|
||||||
</buttonConfiguration>
|
|
||||||
<connections>
|
|
||||||
<action selector="doOpenInstanceURL:" destination="BYZ-38-t0r" eventType="primaryActionTriggered" id="5SW-3o-wiJ"/>
|
|
||||||
</connections>
|
|
||||||
</button>
|
|
||||||
<label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" fixedFrame="YES" text="HotPocket is configured and ready." textAlignment="natural" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="0NJ-Zp-2hC">
|
|
||||||
<rect key="frame" x="20" y="277" width="374" height="21"/>
|
|
||||||
<autoresizingMask key="autoresizingMask" widthSizable="YES" flexibleMaxY="YES"/>
|
|
||||||
<fontDescription key="fontDescription" type="system" pointSize="17"/>
|
|
||||||
<color key="textColor" white="1" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
|
|
||||||
<nil key="highlightedColor"/>
|
|
||||||
</label>
|
|
||||||
<button opaque="NO" contentMode="scaleToFill" fixedFrame="YES" contentHorizontalAlignment="center" contentVerticalAlignment="center" buttonType="system" lineBreakMode="middleTruncation" translatesAutoresizingMaskIntoConstraints="NO" id="wQZ-n6-b0o">
|
|
||||||
<rect key="frame" x="161" y="428" width="92" height="35"/>
|
|
||||||
<autoresizingMask key="autoresizingMask" flexibleMinX="YES" flexibleMaxX="YES" flexibleMaxY="YES"/>
|
|
||||||
<buttonConfiguration key="configuration" style="gray" title="Log out">
|
|
||||||
<color key="baseForegroundColor" name="DangerColor"/>
|
|
||||||
</buttonConfiguration>
|
|
||||||
<connections>
|
|
||||||
<action selector="doLogOut:" destination="BYZ-38-t0r" eventType="primaryActionTriggered" id="iq7-wK-GMu"/>
|
|
||||||
</connections>
|
|
||||||
</button>
|
|
||||||
</subviews>
|
</subviews>
|
||||||
<viewLayoutGuide key="safeArea" id="6Tk-OE-BBY"/>
|
<viewLayoutGuide key="safeArea" id="6Tk-OE-BBY"/>
|
||||||
<color key="backgroundColor" name="BackgroundColor"/>
|
<color key="backgroundColor" name="BackgroundColor"/>
|
||||||
<color key="tintColor" name="AccentColor"/>
|
|
||||||
</view>
|
</view>
|
||||||
<navigationItem key="navigationItem" id="w8s-f0-7E0"/>
|
|
||||||
<connections>
|
<connections>
|
||||||
<outlet property="instanceURLButton" destination="OPO-AY-zgd" id="1Wr-H9-eZ6"/>
|
<outlet property="webView" destination="RDB-ib-igF" id="avx-RC-qRB"/>
|
||||||
<outlet property="logoutButton" destination="wQZ-n6-b0o" id="vco-vP-zvy"/>
|
|
||||||
</connections>
|
</connections>
|
||||||
</viewController>
|
</viewController>
|
||||||
<placeholder placeholderIdentifier="IBFirstResponder" id="dkx-z0-nzr" sceneMemberID="firstResponder"/>
|
<placeholder placeholderIdentifier="IBFirstResponder" id="dkx-z0-nzr" sceneMemberID="firstResponder"/>
|
||||||
</objects>
|
</objects>
|
||||||
<point key="canvasLocation" x="962.31884057971024" y="375"/>
|
<point key="canvasLocation" x="53" y="375"/>
|
||||||
</scene>
|
|
||||||
<!--Authorization View Controller-->
|
|
||||||
<scene sceneID="zfn-5m-i4Y">
|
|
||||||
<objects>
|
|
||||||
<viewController storyboardIdentifier="AuthorizationViewController" id="1Il-xJ-X5Y" customClass="AuthorizationViewController" sceneMemberID="viewController">
|
|
||||||
<view key="view" contentMode="scaleToFill" id="gKn-cL-a2b">
|
|
||||||
<rect key="frame" x="0.0" y="0.0" width="414" height="896"/>
|
|
||||||
<autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
|
|
||||||
<subviews>
|
|
||||||
<view contentMode="scaleToFill" fixedFrame="YES" translatesAutoresizingMaskIntoConstraints="NO" id="Kkk-cr-Leu">
|
|
||||||
<rect key="frame" x="20" y="96" width="374" height="165"/>
|
|
||||||
<autoresizingMask key="autoresizingMask" widthSizable="YES" flexibleMinY="YES" flexibleMaxY="YES"/>
|
|
||||||
<subviews>
|
|
||||||
<imageView clipsSubviews="YES" userInteractionEnabled="NO" contentMode="scaleToFill" horizontalHuggingPriority="251" verticalHuggingPriority="251" fixedFrame="YES" translatesAutoresizingMaskIntoConstraints="NO" id="YXT-lU-mHV">
|
|
||||||
<rect key="frame" x="122" y="0.0" width="128" height="128"/>
|
|
||||||
<autoresizingMask key="autoresizingMask" flexibleMinX="YES" flexibleMaxX="YES" flexibleMaxY="YES"/>
|
|
||||||
<imageReference key="image" image="icon-mac-384.png"/>
|
|
||||||
</imageView>
|
|
||||||
<label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" fixedFrame="YES" text="HotPocket by BTHLabs" textAlignment="center" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="hhk-23-s8H">
|
|
||||||
<rect key="frame" x="0.0" y="136" width="374" height="29"/>
|
|
||||||
<autoresizingMask key="autoresizingMask" widthSizable="YES" flexibleMaxY="YES"/>
|
|
||||||
<fontDescription key="fontDescription" type="system" pointSize="24"/>
|
|
||||||
<color key="textColor" white="1" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
|
|
||||||
<nil key="highlightedColor"/>
|
|
||||||
</label>
|
|
||||||
</subviews>
|
|
||||||
</view>
|
|
||||||
<label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" fixedFrame="YES" text="Instance URL" textAlignment="natural" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="alG-Ve-nxN">
|
|
||||||
<rect key="frame" x="20" y="277" width="374" height="21"/>
|
|
||||||
<autoresizingMask key="autoresizingMask" widthSizable="YES" flexibleMaxY="YES"/>
|
|
||||||
<fontDescription key="fontDescription" type="system" pointSize="17"/>
|
|
||||||
<color key="textColor" white="1" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
|
|
||||||
<nil key="highlightedColor"/>
|
|
||||||
</label>
|
|
||||||
<textField opaque="NO" contentMode="scaleToFill" horizontalHuggingPriority="248" fixedFrame="YES" contentHorizontalAlignment="left" contentVerticalAlignment="center" borderStyle="roundedRect" textAlignment="natural" minimumFontSize="17" translatesAutoresizingMaskIntoConstraints="NO" id="v5s-Uh-qWU" customClass="InstanceURLField">
|
|
||||||
<rect key="frame" x="20" y="306" width="374" height="34"/>
|
|
||||||
<autoresizingMask key="autoresizingMask" widthSizable="YES" flexibleMaxY="YES"/>
|
|
||||||
<color key="backgroundColor" white="0.33333333333333331" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
|
|
||||||
<color key="textColor" white="1" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
|
|
||||||
<fontDescription key="fontDescription" type="system" pointSize="14"/>
|
|
||||||
<textInputTraits key="textInputTraits" autocorrectionType="no" spellCheckingType="no" keyboardType="URL" returnKeyType="go" smartDashesType="no" smartInsertDeleteType="no" smartQuotesType="no" textContentType="url"/>
|
|
||||||
<connections>
|
|
||||||
<action selector="doStartAuthorizationFlow:" destination="1Il-xJ-X5Y" eventType="primaryActionTriggered" id="Rd9-1f-N6Z"/>
|
|
||||||
</connections>
|
|
||||||
</textField>
|
|
||||||
<label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" fixedFrame="YES" text="Enter the URL to your HotPocket instance, e.g. https://my.hotpocket.app" textAlignment="natural" lineBreakMode="tailTruncation" numberOfLines="0" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="Tn1-fl-daL" customClass="MultilineLabel">
|
|
||||||
<rect key="frame" x="20" y="348" width="374" height="64"/>
|
|
||||||
<autoresizingMask key="autoresizingMask" widthSizable="YES" flexibleMaxY="YES"/>
|
|
||||||
<fontDescription key="fontDescription" type="system" pointSize="17"/>
|
|
||||||
<color key="textColor" white="1" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
|
|
||||||
<nil key="highlightedColor"/>
|
|
||||||
</label>
|
|
||||||
<button opaque="NO" contentMode="scaleToFill" fixedFrame="YES" contentHorizontalAlignment="center" contentVerticalAlignment="center" buttonType="system" lineBreakMode="middleTruncation" translatesAutoresizingMaskIntoConstraints="NO" id="eKt-N1-DEJ">
|
|
||||||
<rect key="frame" x="20" y="428" width="374" height="35"/>
|
|
||||||
<autoresizingMask key="autoresizingMask" widthSizable="YES" flexibleMaxY="YES"/>
|
|
||||||
<state key="normal" title="Button"/>
|
|
||||||
<buttonConfiguration key="configuration" style="filled" title="Continue"/>
|
|
||||||
<connections>
|
|
||||||
<action selector="doStartAuthorizationFlow:" destination="1Il-xJ-X5Y" eventType="primaryActionTriggered" id="U0V-Pp-M2x"/>
|
|
||||||
</connections>
|
|
||||||
</button>
|
|
||||||
</subviews>
|
|
||||||
<viewLayoutGuide key="safeArea" id="dL2-4T-yXY"/>
|
|
||||||
<color key="backgroundColor" name="BackgroundColor"/>
|
|
||||||
<color key="tintColor" name="AccentColor"/>
|
|
||||||
</view>
|
|
||||||
<connections>
|
|
||||||
<outlet property="instanceURLField" destination="v5s-Uh-qWU" id="hRQ-r8-3Dz"/>
|
|
||||||
</connections>
|
|
||||||
</viewController>
|
|
||||||
<placeholder placeholderIdentifier="IBFirstResponder" id="m6b-Bm-Ty7" userLabel="First Responder" customClass="UIResponder" sceneMemberID="firstResponder"/>
|
|
||||||
</objects>
|
|
||||||
<point key="canvasLocation" x="1726.0869565217392" y="375"/>
|
|
||||||
</scene>
|
|
||||||
<!--Navigation Controller-->
|
|
||||||
<scene sceneID="zFJ-kU-27j">
|
|
||||||
<objects>
|
|
||||||
<navigationController automaticallyAdjustsScrollViewInsets="NO" id="7Sa-RR-xgc" sceneMemberID="viewController">
|
|
||||||
<toolbarItems/>
|
|
||||||
<navigationBar key="navigationBar" contentMode="scaleToFill" id="PrZ-Cz-0b5">
|
|
||||||
<rect key="frame" x="0.0" y="96" width="414" height="54"/>
|
|
||||||
<autoresizingMask key="autoresizingMask"/>
|
|
||||||
</navigationBar>
|
|
||||||
<nil name="viewControllers"/>
|
|
||||||
<connections>
|
|
||||||
<segue destination="BYZ-38-t0r" kind="relationship" relationship="rootViewController" id="7mY-Zh-QsC"/>
|
|
||||||
</connections>
|
|
||||||
</navigationController>
|
|
||||||
<placeholder placeholderIdentifier="IBFirstResponder" id="GIS-z2-loC" userLabel="First Responder" customClass="UIResponder" sceneMemberID="firstResponder"/>
|
|
||||||
</objects>
|
|
||||||
<point key="canvasLocation" x="52.173913043478265" y="375"/>
|
|
||||||
</scene>
|
|
||||||
<!--Authorization Progress View Controller-->
|
|
||||||
<scene sceneID="689-0y-Gyr">
|
|
||||||
<objects>
|
|
||||||
<viewController storyboardIdentifier="AuthorizationProgressViewController" id="aiy-3v-nI7" customClass="AuthorizationProgressViewController" sceneMemberID="viewController">
|
|
||||||
<view key="view" contentMode="scaleToFill" id="ljp-b5-lta">
|
|
||||||
<rect key="frame" x="0.0" y="0.0" width="414" height="896"/>
|
|
||||||
<autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
|
|
||||||
<subviews>
|
|
||||||
<view contentMode="scaleToFill" fixedFrame="YES" translatesAutoresizingMaskIntoConstraints="NO" id="wKr-WU-Iec">
|
|
||||||
<rect key="frame" x="20" y="96" width="374" height="165"/>
|
|
||||||
<autoresizingMask key="autoresizingMask" widthSizable="YES" flexibleMinY="YES" flexibleMaxY="YES"/>
|
|
||||||
<subviews>
|
|
||||||
<imageView clipsSubviews="YES" userInteractionEnabled="NO" contentMode="scaleToFill" horizontalHuggingPriority="251" verticalHuggingPriority="251" fixedFrame="YES" translatesAutoresizingMaskIntoConstraints="NO" id="v6u-sE-tzJ">
|
|
||||||
<rect key="frame" x="122" y="0.0" width="128" height="128"/>
|
|
||||||
<autoresizingMask key="autoresizingMask" flexibleMinX="YES" flexibleMaxX="YES" flexibleMaxY="YES"/>
|
|
||||||
<imageReference key="image" image="icon-mac-384.png"/>
|
|
||||||
</imageView>
|
|
||||||
<label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" fixedFrame="YES" text="HotPocket by BTHLabs" textAlignment="center" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="50v-cp-DGd">
|
|
||||||
<rect key="frame" x="0.0" y="136" width="374" height="29"/>
|
|
||||||
<autoresizingMask key="autoresizingMask" widthSizable="YES" flexibleMaxY="YES"/>
|
|
||||||
<fontDescription key="fontDescription" type="system" pointSize="24"/>
|
|
||||||
<color key="textColor" white="1" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
|
|
||||||
<nil key="highlightedColor"/>
|
|
||||||
</label>
|
|
||||||
</subviews>
|
|
||||||
</view>
|
|
||||||
<activityIndicatorView opaque="NO" contentMode="scaleToFill" horizontalHuggingPriority="750" verticalHuggingPriority="750" fixedFrame="YES" style="whiteLarge" translatesAutoresizingMaskIntoConstraints="NO" id="DNy-gf-n60">
|
|
||||||
<rect key="frame" x="189" y="306" width="37" height="37"/>
|
|
||||||
<autoresizingMask key="autoresizingMask" flexibleMinX="YES" flexibleMaxX="YES" flexibleMaxY="YES"/>
|
|
||||||
</activityIndicatorView>
|
|
||||||
<label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" fixedFrame="YES" text="Awaiting authentication response..." textAlignment="center" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="qiJ-yx-nMd">
|
|
||||||
<rect key="frame" x="20" y="359" width="374" height="21"/>
|
|
||||||
<autoresizingMask key="autoresizingMask" widthSizable="YES" flexibleMaxY="YES"/>
|
|
||||||
<fontDescription key="fontDescription" type="system" pointSize="17"/>
|
|
||||||
<color key="textColor" white="1" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
|
|
||||||
<nil key="highlightedColor"/>
|
|
||||||
</label>
|
|
||||||
</subviews>
|
|
||||||
<viewLayoutGuide key="safeArea" id="zyd-wv-1rn"/>
|
|
||||||
<color key="backgroundColor" name="BackgroundColor"/>
|
|
||||||
</view>
|
|
||||||
<connections>
|
|
||||||
<outlet property="progressIndicator" destination="DNy-gf-n60" id="hJF-jc-ZJ0"/>
|
|
||||||
</connections>
|
|
||||||
</viewController>
|
|
||||||
<placeholder placeholderIdentifier="IBFirstResponder" id="N3D-cM-5Ro" userLabel="First Responder" customClass="UIResponder" sceneMemberID="firstResponder"/>
|
|
||||||
</objects>
|
|
||||||
<point key="canvasLocation" x="2532" y="375"/>
|
|
||||||
</scene>
|
</scene>
|
||||||
</scenes>
|
</scenes>
|
||||||
<color key="tintColor" name="AccentColor"/>
|
|
||||||
<resources>
|
<resources>
|
||||||
<image name="icon-mac-384.png" width="384" height="384"/>
|
|
||||||
<namedColor name="AccentColor">
|
|
||||||
<color red="0.10980392156862745" green="0.72941176470588232" blue="0.92941176470588238" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
|
|
||||||
</namedColor>
|
|
||||||
<namedColor name="BackgroundColor">
|
<namedColor name="BackgroundColor">
|
||||||
<color red="0.12941176470588237" green="0.14509803921568629" blue="0.16078431372549021" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
|
<color red="0.12941176470588237" green="0.14509803921568629" blue="0.16078431372549021" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
|
||||||
</namedColor>
|
</namedColor>
|
||||||
<namedColor name="DangerColor">
|
|
||||||
<color red="0.93300002813339233" green="0.3919999897480011" blue="0.46299999952316284" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
|
|
||||||
</namedColor>
|
|
||||||
<namedColor name="SecondaryColor">
|
|
||||||
<color red="0.0" green="0.50980392156862742" blue="0.8666666666666667" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
|
|
||||||
</namedColor>
|
|
||||||
</resources>
|
</resources>
|
||||||
</document>
|
</document>
|
||||||
|
|
|
@ -1,15 +0,0 @@
|
||||||
<?xml version="1.0" encoding="UTF-8"?>
|
|
||||||
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
|
|
||||||
<plist version="1.0">
|
|
||||||
<dict>
|
|
||||||
<key>com.apple.security.application-groups</key>
|
|
||||||
<array>
|
|
||||||
<string>group.pl.bthlabs.HotPocket</string>
|
|
||||||
</array>
|
|
||||||
<key>keychain-access-groups</key>
|
|
||||||
<array>
|
|
||||||
<string>$(AppIdentifierPrefix)pl.bthlabs.HotPocketShared</string>
|
|
||||||
<string>$(AppIdentifierPrefix)pl.bthlabs.HotPocket</string>
|
|
||||||
</array>
|
|
||||||
</dict>
|
|
||||||
</plist>
|
|
|
@ -2,34 +2,6 @@
|
||||||
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
|
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
|
||||||
<plist version="1.0">
|
<plist version="1.0">
|
||||||
<dict>
|
<dict>
|
||||||
<key>CFBundleURLTypes</key>
|
|
||||||
<array>
|
|
||||||
<dict>
|
|
||||||
<key>CFBundleTypeRole</key>
|
|
||||||
<string>Viewer</string>
|
|
||||||
<key>CFBundleURLIconFile</key>
|
|
||||||
<string>icon-mac-384</string>
|
|
||||||
<key>CFBundleURLName</key>
|
|
||||||
<string>HotPocketDesktopMac</string>
|
|
||||||
<key>CFBundleURLSchemes</key>
|
|
||||||
<array>
|
|
||||||
<string>hotpocket-mobile</string>
|
|
||||||
</array>
|
|
||||||
</dict>
|
|
||||||
</array>
|
|
||||||
<key>HPAPIAccessTokenPlatform</key>
|
|
||||||
<string>iPhone</string>
|
|
||||||
<key>HPAuthFlowPostAuthenticateURLParts</key>
|
|
||||||
<dict>
|
|
||||||
<key>host</key>
|
|
||||||
<string>post-authenticate</string>
|
|
||||||
<key>scheme</key>
|
|
||||||
<string>hotpocket-mobile</string>
|
|
||||||
</dict>
|
|
||||||
<key>HPAuthFlowSource</key>
|
|
||||||
<string>HotPocketMobile</string>
|
|
||||||
<key>HPRPCClientOrigin</key>
|
|
||||||
<string>hotpocket-mobile://HPRPCClient</string>
|
|
||||||
<key>UIApplicationSceneManifest</key>
|
<key>UIApplicationSceneManifest</key>
|
||||||
<dict>
|
<dict>
|
||||||
<key>UIApplicationSupportsMultipleScenes</key>
|
<key>UIApplicationSupportsMultipleScenes</key>
|
||||||
|
|
|
@ -1,16 +0,0 @@
|
||||||
//
|
|
||||||
// InstanceURLField.h
|
|
||||||
// HotPocket (macOS)
|
|
||||||
//
|
|
||||||
// Created by Tomek Wójcik on 30/09/2025.
|
|
||||||
//
|
|
||||||
|
|
||||||
#import <UIKit/UIKit.h>
|
|
||||||
|
|
||||||
NS_ASSUME_NONNULL_BEGIN
|
|
||||||
|
|
||||||
@interface InstanceURLField : UITextField
|
|
||||||
|
|
||||||
@end
|
|
||||||
|
|
||||||
NS_ASSUME_NONNULL_END
|
|
|
@ -1,21 +0,0 @@
|
||||||
//
|
|
||||||
// InstanceURLField.m
|
|
||||||
// HotPocket (macOS)
|
|
||||||
//
|
|
||||||
// Created by Tomek Wójcik on 30/09/2025.
|
|
||||||
//
|
|
||||||
|
|
||||||
#import "InstanceURLField.h"
|
|
||||||
|
|
||||||
@implementation InstanceURLField
|
|
||||||
|
|
||||||
-(CGRect)rightViewRectForBounds:(CGRect)bounds {
|
|
||||||
if (self.rightViewMode != UITextFieldViewModeNever) {
|
|
||||||
CGFloat offsetTop = (bounds.size.height - 16.0) / 2.0;
|
|
||||||
return CGRectMake(bounds.size.width - 16.0 - offsetTop, offsetTop, 16.0, 16.0);
|
|
||||||
}
|
|
||||||
|
|
||||||
return CGRectNull;
|
|
||||||
}
|
|
||||||
|
|
||||||
@end
|
|
|
@ -1,22 +0,0 @@
|
||||||
//
|
|
||||||
// MainViewController.h
|
|
||||||
// HotPocket (iOS)
|
|
||||||
//
|
|
||||||
// Created by Tomek Wójcik on 25/09/2025.
|
|
||||||
//
|
|
||||||
|
|
||||||
#import <UIKit/UIKit.h>
|
|
||||||
|
|
||||||
NS_ASSUME_NONNULL_BEGIN
|
|
||||||
|
|
||||||
@interface MainViewController : UIViewController
|
|
||||||
|
|
||||||
@property IBOutlet UIButton *instanceURLButton;
|
|
||||||
@property IBOutlet UIButton *logoutButton;
|
|
||||||
|
|
||||||
-(IBAction)doOpenInstanceURL:(id)sender;
|
|
||||||
-(IBAction)doLogOut:(id)sender;
|
|
||||||
|
|
||||||
@end
|
|
||||||
|
|
||||||
NS_ASSUME_NONNULL_END
|
|