Appearance
Are you an LLM? You can read better optimized documentation at /app/account-sign-in-and-permissions.md for this page in Markdown format
Home › Help › Account, sign-in, and permissions
Account, sign-in, and permissions
ShootCal does not make you create a separate username or password. You sign in with your existing Google account, and Google itself handles the login. ShootCal never sees your Google password.
When you sign in, ShootCal asks Google for permission to do specific things on your behalf, like read and create calendar events, save clients to Google Contacts, and send confirmation emails from your own Gmail. You see exactly what you are agreeing to on Google's consent screen, and you can decline.
A few extra features ask for permission only the first time you use them, not at sign-in. Tasks and the "find client emails from my Google contacts" scan are two examples. This keeps the normal sign-in simple and avoids an extra warning screen for features you may never turn on.
While those few features are still being reviewed by Google, turning one on may show a "this app is not verified by Google" notice. That is a normal step for a newer app and does not mean anything is wrong. You can always remove ShootCal's access to your Google account at any time from your Google Account security page, with no help from us needed.
Sign-in is Google OAuth 2.0, not a ShootCal password
ShootCal has no password of its own. Identity comes entirely from Google.
On the web app, the browser is sent to Google's consent screen, then Google sends you back to ShootCal once you approve. ShootCal uses Google's standard secure login flow (OAuth with PKCE), so ShootCal never sees your password and the login handshake is protected end to end. Your identity comes straight from Google to ShootCal's server, never through the browser, and the server double-checks that it really came from Google and was meant for ShootCal before trusting it. (The full handshake details, including how the short-lived handshake cookie is protected, are on the privacy page.)
On the native apps (iPhone, iPad, Mac), sign-in uses Google's official GoogleSignIn SDK with ShootCal's own iOS OAuth client id. The SDK presents Google's screen, and on a later launch it can silently restore a prior session so you do not have to sign in again every time.
The exact scopes requested at sign-in, and why each is needed
The web and native sign-ins request overlapping but not identical permission sets. They share the calendar, contacts, and gmail.send scopes, but the web sign-in also asks for basic identity (openid, email, profile) and a Drive scope for the contract archive, while the native sign-in has neither (the GoogleSignIn SDK supplies your identity, and the Drive feature is web-only). At a normal sign-in ShootCal requests:
- openid, email, profile (web), basic identity: your Google account id, email, and name/photo. This is what tells ShootCal who you are. (On native, identity comes from the GoogleSignIn SDK, so these are not in the native scope list.)
- calendar.events, create and edit your sessions/bookings as calendar events.
- calendar.readonly, list your calendars and read existing events.
- contacts, the client manager, which reads and writes Google Contacts so clients sync.
- gmail.send, send the photographer's OWN notification and confirmation emails from their connected Gmail. This is send-only: it cannot read the mailbox. If you decline it, sends fail gracefully and the underlying booking is still saved.
- drive.file (web only), used by the signed-contract archive. This scope only ever lets the app see or manage files it created itself, so it can only ever reach ShootCal's own "ShootCal Contracts" folder. It cannot browse the rest of your Drive.
All of these are Google-classified as "sensitive," not "restricted" (there is no full-mailbox read), so they need consent-screen verification but not a paid third-party security audit.
Incremental consent: Tasks and read-only "Other contacts" are asked on first use, not at sign-in
Two scopes are deliberately kept OUT of the sign-in request and asked for only when you first use the feature that needs them:
- Other contacts (read-only), read-only access to your auto-saved "Other contacts" (people you have emailed), used by the optional "find client emails from my Google contacts" step of the calendar scan.
Why split it out? It's a privacy-first design: this is a narrow, optional feature, so users who never turn it on never grant the permission. (All of ShootCal's Google permissions completed Google's OAuth verification in July 2026 — no warnings appear anywhere.)
On the web, connecting one of these features re-runs Google consent and adds only the new scope. You must already be signed in. The request explicitly forces Google to show the consent screen even to a returning user, and tells Google to keep all of your existing grants so the resulting token carries both the old and new permissions.
On native, the app asks the SDK to add just the new scope, which presents consent WITHOUT a full sign-out, so your existing Calendar grant is never lost. Tasks additionally has a hard guard: that opt-in flow is the only place the Tasks scope is ever requested, so nothing else in the app can trigger the consent prompt.
Note: gmail.send and contacts were also incremental historically, but were later moved into the sign-in bundle; the native apps now bundle Tasks at sign-in too. Only the "Other contacts" scope remains strictly incremental, tied to its opt-in feature.
Verification status
All of ShootCal's Google permissions are fully verified by Google (OAuth app verification completed July 2026), so no "unverified app" notice appears at sign-in or when enabling any feature. When the web app loads, the server tells it which optional permissions you currently hold, so the UI shows a "Connect Google Tasks" prompt where needed rather than silently failing.
Where the data actually lives
Web: After a successful sign-in, your Google connection is stored on ShootCal's server, encrypted before it is written to disk and kept outside the public website. Your browser holds ONLY a meaningless session token in a locked-down cookie; the server stores only a scrambled, one-way version of it, so a database leak yields no usable cookies. Your identity is figured out solely from that server-side login record, never from anything the browser sends, which is the guarantee that one user can never see another user's calendar. You stay signed in for up to 90 days, refreshed each time you use the app. (The encryption is covered in full on the privacy page.)
Native: OAuth tokens are held by Google's GoogleSignIn SDK, which stores them in the device Keychain; the app's own small Keychain wrapper stores separate web-integration tokens (session/push tokens) as generic-password items, explicitly NOT iCloud-synced. The native app keeps a live snapshot of your granted scopes so the UI can show exactly which permissions you have granted.
The access token is short-lived; the app refreshes it from the stored refresh token as needed, on both the server and natively.
Revoking access and signing out
There are two distinct actions:
Signing out ends your ShootCal session but does not revoke Google's grant. On web, signing out deletes the server session row and clears the cookie. On native, it clears the local session and purges cached event files and the saved calendar selection for a clean reset. The web app can also hold several Google accounts at once: the account menu in the header lets you add and switch between them without signing in again. If you are signed in to more than one, signing out ends only the active account's session and switches you to the next; signing out of the last account ends the session entirely.
Revoking ShootCal's access to your Google account is done on Google's side, not inside ShootCal: visit your Google Account, then Security, then "Third-party apps with account access" (myaccount.google.com/permissions) and remove ShootCal. ShootCal is built to handle this gracefully: when a Google call later fails because the grant was revoked, the native app clears the dead session and re-shows the sign-in prompt (a light reset that keeps your cached events so re-consenting is seamless). A non-network token-refresh failure is treated the same way.
FAQ
Does ShootCal ever see or store my Google password?
No. Sign-in is Google's standard secure login (OAuth). Google handles the login on its own pages and returns only access tokens and a signed proof of who you are. ShootCal stores those tokens (encrypted on the web backend, in the device Keychain on native), never a password. There is no ShootCal password at all.
Can the gmail.send scope read my email?
No. The gmail.send scope is send-only and cannot read the mailbox. It is used solely to send the photographer's own notification and confirmation emails from their connected Gmail. None of ShootCal's scopes include full-mailbox read; all requested scopes are Google-classified 'sensitive,' not 'restricted.'
Are ShootCal's Google permissions verified?
Yes. ShootCal completed Google's OAuth app verification for every permission it requests (July 2026), so you will never see an "unverified app" warning — not at sign-in and not when enabling any feature. If you connected Tasks before verification completed, your grant carries over unchanged.
If I grant an extra scope later, do I lose my existing Calendar permission?
No. On web, the incremental consent request tells Google to keep all prior grants, so the new token carries both old and new scopes. On native, the SDK adds the new scope without a full sign-out, so your existing Calendar grant is untouched. The native app keeps a live snapshot of your granted scopes so the UI reflects exactly what you hold.
Does the drive.file scope let ShootCal read my whole Google Drive?
No. The Drive scope (web only, used for the signed-contract archive) limits the app to files it created itself. It can only ever reach ShootCal's own 'ShootCal Contracts' folder. It cannot browse or read the rest of your Drive.
How is my Google connection protected on the server?
It is encrypted before it is written to disk, with the key kept in a separate file outside the public website, so a database leak alone yields nothing usable. Your browser never holds the Google token; it holds only a meaningless session cookie, and the server stores only a scrambled, one-way version of it, not the value itself. The privacy page covers the exact encryption.
How do I completely revoke ShootCal's access, and what happens in the app afterward?
Signing out inside ShootCal only ends your session. To revoke the OAuth grant, go to your Google Account security page (myaccount.google.com/permissions) and remove ShootCal. Afterward, the next Google call fails, the native app clears the session and re-shows the sign-in prompt while keeping cached events so re-consenting is seamless.
What stops one ShootCal web user from seeing another user's calendar?
Server-side isolation. Your identity is figured out solely from the server's own login record, matched to your session cookie; the browser never sends a user id or calendar owner that the server trusts. Every request resolves the user from that record, so a user can only ever reach their own connected Google data.
What's the difference between a full sign-out and the "expired credentials" path on native?
Signing out is a full reset: it clears the session and purges cached event files plus the saved calendar selection. The expired-credentials path (fired when a Google call fails after a revoke or a non-network refresh failure) is a light reset: it clears the dead session so the sign-in prompt reappears but deliberately keeps cached events and calendar selection, so re-consenting after a revoke or password change doesn't force a full re-setup. ← Back to Help Center