Skip to content
New issue

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

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

Already on GitHub? Sign in to your account

feat(storage): add createSignedURLs method #273

Merged
merged 2 commits into from
Mar 21, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
24 changes: 24 additions & 0 deletions Examples/Examples.xcodeproj/project.pbxproj
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,10 @@
7962989D2AEBC6F9000AA957 /* SVGView in Frameworks */ = {isa = PBXBuildFile; productRef = 7962989C2AEBC6F9000AA957 /* SVGView */; };
79719ECE2ADF26C400737804 /* Supabase in Frameworks */ = {isa = PBXBuildFile; productRef = 79719ECD2ADF26C400737804 /* Supabase */; };
797D664A2B46A1D8007592ED /* Dependencies.swift in Sources */ = {isa = PBXBuildFile; fileRef = 797D66492B46A1D8007592ED /* Dependencies.swift */; };
797EFB662BABD82A00098D6B /* BucketList.swift in Sources */ = {isa = PBXBuildFile; fileRef = 797EFB652BABD82A00098D6B /* BucketList.swift */; };
797EFB682BABD90500098D6B /* Stringfy.swift in Sources */ = {isa = PBXBuildFile; fileRef = 797EFB672BABD90500098D6B /* Stringfy.swift */; };
797EFB6A2BABDF3800098D6B /* BucketDetailView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 797EFB692BABDF3800098D6B /* BucketDetailView.swift */; };
797EFB6C2BABE1B800098D6B /* FileObjectDetailView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 797EFB6B2BABE1B800098D6B /* FileObjectDetailView.swift */; };
7993B8A92B3C673A009B610B /* AuthView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7993B8A82B3C673A009B610B /* AuthView.swift */; };
7993B8AB2B3C67E0009B610B /* Toast.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7993B8AA2B3C67E0009B610B /* Toast.swift */; };
79AF047F2B2CE207008761AD /* AuthWithEmailAndPassword.swift in Sources */ = {isa = PBXBuildFile; fileRef = 79AF047E2B2CE207008761AD /* AuthWithEmailAndPassword.swift */; };
Expand Down Expand Up @@ -87,6 +91,10 @@
796298982AEBBA77000AA957 /* MFAFlow.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MFAFlow.swift; sourceTree = "<group>"; };
7962989A2AEBBD9F000AA957 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist; path = Info.plist; sourceTree = "<group>"; };
797D66492B46A1D8007592ED /* Dependencies.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Dependencies.swift; sourceTree = "<group>"; };
797EFB652BABD82A00098D6B /* BucketList.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = BucketList.swift; sourceTree = "<group>"; };
797EFB672BABD90500098D6B /* Stringfy.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Stringfy.swift; sourceTree = "<group>"; };
797EFB692BABDF3800098D6B /* BucketDetailView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = BucketDetailView.swift; sourceTree = "<group>"; };
797EFB6B2BABE1B800098D6B /* FileObjectDetailView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = FileObjectDetailView.swift; sourceTree = "<group>"; };
7993B8A82B3C673A009B610B /* AuthView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AuthView.swift; sourceTree = "<group>"; };
7993B8AA2B3C67E0009B610B /* Toast.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Toast.swift; sourceTree = "<group>"; };
7993B8AC2B3C97B6009B610B /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist; path = Info.plist; sourceTree = "<group>"; };
Expand Down Expand Up @@ -182,6 +190,7 @@
793895C82954ABFF0044F2B8 /* Examples */ = {
isa = PBXGroup;
children = (
797EFB642BABD7FF00098D6B /* Storage */,
79AF04822B2CE3BD008761AD /* Auth */,
7962989A2AEBBD9F000AA957 /* Info.plist */,
793895CD2954AC000044F2B8 /* Assets.xcassets */,
Expand All @@ -201,6 +210,7 @@
793E03082B2CED5D00AC7DED /* Contants.swift */,
793E030A2B2CEDDA00AC7DED /* ActionState.swift */,
79E2B55B2B97A2310042CD21 /* UIApplicationExtensions.swift */,
797EFB672BABD90500098D6B /* Stringfy.swift */,
);
path = Examples;
sourceTree = "<group>";
Expand All @@ -220,6 +230,16 @@
name = Frameworks;
sourceTree = "<group>";
};
797EFB642BABD7FF00098D6B /* Storage */ = {
isa = PBXGroup;
children = (
797EFB652BABD82A00098D6B /* BucketList.swift */,
797EFB692BABDF3800098D6B /* BucketDetailView.swift */,
797EFB6B2BABE1B800098D6B /* FileObjectDetailView.swift */,
);
path = Storage;
sourceTree = "<group>";
};
79AF04822B2CE3BD008761AD /* Auth */ = {
isa = PBXGroup;
children = (
Expand Down Expand Up @@ -452,6 +472,7 @@
7956406A2955AFBD0088A06F /* ErrorText.swift in Sources */,
79AF04812B2CE261008761AD /* AuthView.swift in Sources */,
794EF1242955F3DE008C9526 /* TodoListRow.swift in Sources */,
797EFB662BABD82A00098D6B /* BucketList.swift in Sources */,
79E2B55C2B97A2310042CD21 /* UIApplicationExtensions.swift in Sources */,
794EF1222955F26A008C9526 /* AddTodoListView.swift in Sources */,
7956405E2954ADE00088A06F /* Secrets.swift in Sources */,
Expand All @@ -462,6 +483,9 @@
795640622955AD2B0088A06F /* HomeView.swift in Sources */,
7940E3152B36187A0089BEE1 /* GoogleSignInWithWebFlow.swift in Sources */,
793895CA2954ABFF0044F2B8 /* ExamplesApp.swift in Sources */,
797EFB682BABD90500098D6B /* Stringfy.swift in Sources */,
797EFB6C2BABE1B800098D6B /* FileObjectDetailView.swift in Sources */,
797EFB6A2BABDF3800098D6B /* BucketDetailView.swift in Sources */,
793E030D2B2DAB5700AC7DED /* SignInWithApple.swift in Sources */,
793E030B2B2CEDDA00AC7DED /* ActionState.swift in Sources */,
);
Expand Down
18 changes: 10 additions & 8 deletions Examples/Examples/Auth/AuthView.swift
Original file line number Diff line number Diff line change
Expand Up @@ -27,16 +27,18 @@ struct AuthView: View {
}

var body: some View {
List {
ForEach(Option.allCases, id: \.self) { option in
NavigationLink(option.title, value: option)
NavigationStack {
List {
ForEach(Option.allCases, id: \.self) { option in
NavigationLink(option.title, value: option)
}
}
.navigationDestination(for: Option.self) { options in
options
.navigationTitle(options.title)
}
.navigationBarTitleDisplayMode(.inline)
}
.navigationDestination(for: Option.self) { options in
options
.navigationTitle(options.title)
}
.navigationBarTitleDisplayMode(.inline)
}
}

Expand Down
7 changes: 3 additions & 4 deletions Examples/Examples/Auth/AuthWithEmailAndPassword.swift
Original file line number Diff line number Diff line change
Expand Up @@ -46,10 +46,6 @@ struct AuthWithEmailAndPassword: View {
}
}

if case let .result(.failure(error)) = actionState {
ErrorText(error)
}

switch actionState {
case .idle:
EmptyView()
Expand Down Expand Up @@ -86,6 +82,7 @@ struct AuthWithEmailAndPassword: View {
.animation(.default, value: mode)
}

@MainActor
func primaryActionButtonTapped() async {
do {
actionState = .inFlight
Expand All @@ -110,6 +107,7 @@ struct AuthWithEmailAndPassword: View {
}
}

@MainActor
private func onOpenURL(_ url: URL) async {
do {
try await supabase.auth.session(from: url)
Expand All @@ -118,6 +116,7 @@ struct AuthWithEmailAndPassword: View {
}
}

@MainActor
private func resendConfirmationButtonTapped() async {
do {
try await supabase.auth.resend(email: email, type: .signup)
Expand Down
11 changes: 7 additions & 4 deletions Examples/Examples/ExamplesApp.swift
Original file line number Diff line number Diff line change
Expand Up @@ -22,8 +22,11 @@ struct ExamplesApp: App {
let supabase = SupabaseClient(
supabaseURL: Secrets.supabaseURL,
supabaseKey: Secrets.supabaseAnonKey,
options: .init(auth: .init(storage: KeychainLocalStorage(
service: "supabase.gotrue.swift",
accessGroup: nil
)))
options: .init(global: .init(logger: ConsoleLogger()))
)

struct ConsoleLogger: SupabaseLogger {
func log(message: SupabaseLogMessage) {
print(message)
}
}
36 changes: 20 additions & 16 deletions Examples/Examples/HomeView.swift
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
// Created by Guilherme Souza on 23/12/22.
//

import Supabase
import SwiftUI

struct HomeView: View {
Expand All @@ -13,28 +14,31 @@ struct HomeView: View {
@State private var mfaStatus: MFAStatus?

var body: some View {
TodoListView()
.toolbar {
ToolbarItemGroup(placement: .cancellationAction) {
Button("Sign out") {
Task {
try! await supabase.auth.signOut()
}
NavigationStack {
BucketList()
.navigationDestination(for: Bucket.self, destination: BucketDetailView.init)
}
.toolbar {
ToolbarItemGroup(placement: .cancellationAction) {
Button("Sign out") {
Task {
try! await supabase.auth.signOut()
}
}

Button("Reauthenticate") {
Task {
try! await supabase.auth.reauthenticate()
}
Button("Reauthenticate") {
Task {
try! await supabase.auth.reauthenticate()
}
}
}
.task {
}
.task {
// mfaStatus = await verifyMFAStatus()
}
.sheet(unwrapping: $mfaStatus) { $mfaStatus in
MFAFlow(status: mfaStatus)
}
}
.sheet(unwrapping: $mfaStatus) { $mfaStatus in
MFAFlow(status: mfaStatus)
}
}

private func verifyMFAStatus() async -> MFAStatus? {
Expand Down
10 changes: 4 additions & 6 deletions Examples/Examples/RootView.swift
Original file line number Diff line number Diff line change
Expand Up @@ -12,12 +12,10 @@ struct RootView: View {
@Environment(AuthController.self) var auth

var body: some View {
NavigationStack {
if auth.session == nil {
AuthView()
} else {
HomeView()
}
if auth.session == nil {
AuthView()
} else {
HomeView()
}
}
}
Expand Down
87 changes: 87 additions & 0 deletions Examples/Examples/Storage/BucketDetailView.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,87 @@
//
// BucketDetailView.swift
// Examples
//
// Created by Guilherme Souza on 21/03/24.
//

import Supabase
import SwiftUI

struct BucketDetailView: View {
let bucket: Bucket

@State private var fileObjects = ActionState<[FileObject], Error>.idle
@State private var presentBucketDetails = false

var body: some View {
Group {
switch fileObjects {
case .idle:
Color.clear
case .inFlight:
ProgressView()
case let .result(.success(files)):
List {
ForEach(files) { file in
NavigationLink(file.name, value: file)
}
}
case let .result(.failure(error)):
VStack {
ErrorText(error)
Button("Retry") {
Task { await load() }
}
}
}
}
.task { await load() }
.navigationTitle("Objects")
.toolbar {
ToolbarItem(placement: .primaryAction) {
Button {
presentBucketDetails = true
} label: {
Label("Detail", systemImage: "info.circle")
}
}
}
.popover(isPresented: $presentBucketDetails) {
ScrollView {
Text(stringfy(bucket))
.monospaced()
.frame(maxWidth: .infinity, alignment: .leading)
.padding()
}
}
.navigationDestination(for: FileObject.self) {
FileObjectDetailView(api: supabase.storage.from(bucket.id), fileObject: $0)
}
}

@MainActor
private func load() async {
fileObjects = .inFlight
fileObjects = await .result(
Result {
try await supabase.storage.from(bucket.id).list()
}
)
}
}

#Preview {
BucketDetailView(
bucket: Bucket(
id: UUID().uuidString,
name: "name",
owner: "owner",
isPublic: false,
createdAt: Date(),
updatedAt: Date(),
allowedMimeTypes: nil,
fileSizeLimit: nil
)
)
}
75 changes: 75 additions & 0 deletions Examples/Examples/Storage/BucketList.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,75 @@
//
// BucketList.swift
// Examples
//
// Created by Guilherme Souza on 21/03/24.
//

import Supabase
import SwiftUI

struct BucketList: View {
@State var buckets = ActionState<[Bucket], Error>.idle

var body: some View {
Group {
switch buckets {
case .idle:
Color.clear
case .inFlight:
ProgressView()
case let .result(.success(buckets)):
List {
ForEach(buckets, id: \.self) { bucket in
NavigationLink(bucket.name, value: bucket)
}
}
.overlay {
if buckets.isEmpty {
Text("No buckets found.")
}
}
case let .result(.failure(error)):
VStack {
ErrorText(error)
Button("Retry") {
Task {
await load()
}
}
}
}
}
.task {
await load()
}
.navigationTitle("Bucket list")
.toolbar {
ToolbarItem(placement: .primaryAction) {
Button("Add") {
Task {
do {
try await supabase.storage.createBucket("bucket-\(UUID().uuidString)")
await load()
} catch {}
}
}
}
}
}

@MainActor
private func load() async {
do {
self.buckets = .inFlight
let buckets = try await supabase.storage.listBuckets()
self.buckets = .result(.success(buckets))
} catch {
buckets = .result(.failure(error))
}
}
}

#Preview {
BucketList()
}
Loading
Loading