Google Cloud Console에 로그인합니다: Google Cloud Console
프로젝트 선택:
상단에서 프로젝트 이름(storage 등)을 클릭하여 올바른 프로젝트를 선택합니다.
API 및 서비스 > 사용자 인증 정보로 이동:
왼쪽 사이드바 메뉴에서 API 및 서비스 > 사용자 인증 정보를 선택합니다.
OAuth 2.0 클라이언트 ID 편집:
사용자 인증 정보 페이지에서 OAuth 2.0 클라이언트 ID를 찾아 클릭하여 설정을 엽니다.
승인된 리디렉션 URI 수정:
리디렉션 URI란에 코드에서 사용 중인 리디렉션 URI와 동일한 URL을 추가합니다.
예를 들어, 코드에서 사용하고 있는 URI가 https://8440.co.kr/drive/index.php라면, https://8440.co.kr/drive/index.php를 승인된 리디렉션 URI에 추가해야 합니다.
변경사항 저장:
설정을 완료한 후 저장 버튼을 클릭하여 변경사항을 저장합니다.
코드와 Google Cloud Console의 리디렉션 URI 확인
코드에서 설정된 리디렉션 URI는 아래 부분입니다.
$client->setRedirectUri('https://8440.co.kr/drive/index.php');
이 값이 Google Cloud Console의 승인된 리디렉션 URI 목록에 정확히 일치하게 추가되어야 합니다.
다시 시도
설정을 수정하고 저장한 후 다시 Google 인증을 시도하면 문제가 해결될 것입니다.
나의 말:
Fatal error: Uncaught InvalidArgumentException: invalid json token in /mirae8440/www/vendor/google/apiclient/src/Client.php:500 Stack trace: #0 /mirae8440/www/googledrive/index.php(21): Google\Client->setAccessToken(NULL) #1 {main} thrown in /mirae8440/www/vendor/google/apiclient/src/Client.php on line 500
ChatGPT의 말:
ChatGPT
이 오류는 Google_Client->setAccessToken() 메서드에 전달된 액세스 토큰이 잘못되었거나 null 값이어서 발생한 문제입니다. 이 문제는 보통 토큰 파일이 비어 있거나 JSON 형식이 잘못되었을 때 나타납니다.
해결 방법
토큰 파일이 제대로 저장되었는지 확인합니다.
token.json 파일이 존재하고, JSON 형식으로 액세스 토큰이 저장되어 있는지 확인하세요.
파일이 비어 있거나 잘못된 형식이라면, OAuth 인증을 다시 수행하여 토큰 파일을 새로 생성해야 합니다.
코드에서 토큰 파일 읽기 및 예외 처리 추가:
파일이 비어 있을 때 오류가 발생하지 않도록, 파일 내용을 읽을 때 유효성을 검사하는 코드를 추가해 보세요.
수정된 코드 예제
아래 코드는 token.json 파일이 존재하지 않거나 잘못된 JSON 형식인 경우를 처리할 수 있도록 합니다.
<?php
require_once $_SERVER['DOCUMENT_ROOT'] . '/vendor/autoload.php';
session_start();
// Google OAuth2 클라이언트 설정
$client = new Google_Client();
$client->setClientId('590016082672-nbj1qblqunvl2fcplt6eupcu7db4jqthttp://m.apps.googleusercontent.com');
$client->setClientSecret('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');
$client->setRedirectUri('https://8440.co.kr/drive/index.php');
$client->addScope(Google_Service_Drive::DRIVE);
// 토큰 파일 경로 설정
$tokenFile = $_SERVER['DOCUMENT_ROOT'] . '/tokens/token.json';
// 토큰 파일이 존재하는지 확인하고 유효한지 검사
if (file_exists($tokenFile) && $accessToken = json_decode(file_get_contents($tokenFile), true)) {
// 유효한 JSON 형식의 토큰이 있는 경우 설정
$client->setAccessToken($accessToken);
// 만약 토큰이 만료되었으면 리프레시 토큰을 사용해 갱신하고 파일에 다시 저장
if ($client->isAccessTokenExpired()) {
$client->fetchAccessTokenWithRefreshToken($client->getRefreshToken());
file_put_contents($tokenFile, json_encode($client->getAccessToken()));
}
} else {
// 토큰 파일이 없거나 JSON 형식이 잘못된 경우, OAuth 인증 절차 수행
if (!isset($_GET['code'])) {
$authUrl = $client->createAuthUrl();
echo "<a href='$authUrl'>구글 드라이브 인증</a>";
exit;
} else {
// 사용자가 인증을 완료하고 돌아오면 액세스 토큰을 받아서 파일에 저장
$client->authenticate($_GET['code']);
$accessToken = $client->getAccessToken();
// 새로 발급받은 토큰을 파일에 저장
file_put_contents($tokenFile, json_encode($accessToken));
header('Location: ' . filter_var($client->getRedirectUri(), FILTER_SANITIZE_URL));
exit;
}
}
// Google Drive 서비스 초기화 및 파일 업로드
$service = new Google_Service_Drive($client);
// 파일 업로드 등의 작업 수행
?>
코드 설명
토큰 파일 존재 및 JSON 유효성 검사:
file_exists($tokenFile)로 파일이 존재하는지 확인하고, json_decode()로 파일 내용을 읽어 JSON이 유효한지 검사합니다.
유효하지 않은 경우 인증 프로세스 수행:
토큰 파일이 없거나 JSON 형식이 잘못된 경우, OAuth 인증을 통해 새로운 토큰을 발급받아 token.json 파일에 저장합니다.
추가 주의 사항
token.json 파일이 정확한 위치에 있고, 해당 파일에 유효한 JSON 형식으로 토큰이 저장되어 있어야 합니다.
위 코드를 통해 문제가 해결되지 않으면, token.json 파일을 삭제하고 다시 인증 절차를 수행해 보세요.
나의 말:
웹사이트에 파일의 입출력하는 것을 꼭 OAuth2.0을 해야 하나?
내가 구글 아이디와 API키만 있으면 실행하는 간단한 방법은 없을까?
ChatGPT의 말:
ChatGPT
Google Drive API를 통해 웹사이트에서 파일을 업로드, 다운로드, 삭제하려면 OAuth 2.0 인증이 필요합니다. Google Drive는 사용자 데이터에 접근하기 때문에 OAuth 2.0 인증을 통해 사용자에게 명시적으로 권한을 요청하는 절차가 필수입니다. 단순히 API 키나 Google 계정만으로는 사용자 데이터를 다룰 수 없습니다.
하지만 특정 시나리오에서는 서비스 계정을 통해 OAuth 2.0을 최소화하여 간단하게 사용할 수 있는 방법이 있습니다. 이 방법은 서버 간의 통신에서 유용하며, 개인 Google Drive보다는 Google Workspace의 공유 드라이브에 주로 사용됩니다.
1. Google 서비스 계정 사용
서비스 계정은 OAuth 인증을 사용하지만 사용자 권한 요청 없이 백그라운드에서 자동으로 작동합니다. 일반적으로 Google Workspace의 공유 드라이브에 접근할 때 유용합니다.
Google Cloud Console에서 서비스 계정을 생성합니다.
생성된 서비스 계정의 JSON 키 파일을 다운로드하여 PHP 코드에서 사용합니다.
서비스 계정으로 Google Drive에 접근할 수 있도록 Google Workspace 관리자에게 권한을 요청합니다.
참고: 개인 Google Drive에 접근할 때는 서비스 계정 사용이 제한적입니다. Google Workspace 계정의 공유 드라이브에서 파일을 관리하는 경우에 주로 사용됩니다.
2. API 키만으로 가능한 작업 (공개 데이터에 한정)
API 키만으로는 사용자 데이터를 다룰 수 없습니다. 하지만 Google Drive에 공개된 파일을 접근하는 데는 사용할 수 있습니다. 예를 들어, 공개된 파일을 다운로드하는 경우 API 키로 접근할 수 있지만, 업로드, 삭제 등의 작업은 지원되지 않습니다.
<?php
$apiKey = 'YOUR_API_KEY';
$fileId = 'PUBLIC_FILE_ID';
$url = "https://www.googleapis.com/drive/v3/files/$fileId?alt=media&key=$apiKey";
$response = file_get_contents($url);
if ($response !== false) {
file_put_contents('downloaded_file', $response);
echo "파일 다운로드 완료!";
} else {
echo "다운로드에 실패했습니다.";
}
?>
위 코드 예제는 공개된 Google Drive 파일을 API 키로 다운로드하는 방법을 보여줍니다.
요약
OAuth 2.0: Google Drive의 모든 파일 관리 작업에 필수입니다.
서비스 계정: Google Workspace의 공유 드라이브에 접근할 때 유용합니다.
API 키만 사용: 공개된 파일에만 접근이 가능하며, 제한적인 작업에 사용됩니다.
따라서 Google Drive의 파일 입출력을 웹사이트에서 원활히 사용하려면 OAuth 2.0 인증이 필요합니다.
나의 말:
결국 대용량 파일의 업로드 및 관리를 하려면 OAuth2.0을 통해야 한다는 말이지?
ChatGPT의 말:
ChatGPT
네, 맞습니다. Google Drive에서 대용량 파일을 업로드하거나 관리하려면 반드시 OAuth 2.0 인증을 통해야 합니다. Google Drive API는 개인 또는 조직의 파일에 접근하는 것이기 때문에, 사용자나 관리자에게 명시적으로 권한을 부여받는 과정이 필수입니다.
요약하자면:
OAuth 2.0 인증은 필수입니다. 사용자 계정의 Google Drive 파일에 접근, 업로드, 삭제 등의 작업을 수행할 수 있게 허용합니다.
서비스 계정을 사용하여 Google Workspace의 공유 드라이브와 같은 일부 시나리오에서 자동화된 접근을 할 수 있지만, 여전히 OAuth 2.0을 통해 승인된 서비스 계정을 사용해야 합니다.
단순 API 키만으로는 공개된 데이터에 한정하여 읽기 전용 작업만 가능합니다.
따라서 OAuth 2.0 인증을 통해 필요한 파일 관리 작업을 구현해야 합니다.
나의 말:
난 구글 console을 통해서 하는 절차가 너무 어렵다. 일단 OAuth2.0 인증을 위한 절차가 너무 어려워. 지금 위에서 설명한대로 차근차근하고 있지만, 안된다.
ChatGPT의 말:
ChatGPT
Google Drive API를 처음 설정하고 OAuth 2.0 인증을 적용하는 과정은 다소 복잡할 수 있습니다. 절차가 익숙하지 않으면 특히 어렵게 느껴질 수 있습니다. 이해를 돕기 위해, Google Drive API를 설정하고 OAuth 2.0 인증을 적용하는 전체 과정을 단계별로 간소화된 방식으로 정리해 보겠습니다.
단계별 간단한 설정 가이드
1. Google Cloud Console에서 프로젝트 생성 및 API 활성화
Google Cloud Console에 접속합니다: https://console.cloud.google.com/
새 프로젝트를 생성합니다. (왼쪽 상단의 프로젝트 선택 메뉴에서 '프로젝트 만들기' 선택)
생성된 프로젝트에서 API 및 서비스 > 라이브러리로 이동합니다.
Google Drive API를 검색하여 활성화합니다.
2. OAuth 2.0 클라이언트 설정
API 및 서비스 > 사용자 인증 정보로 이동합니다.
OAuth 동의 화면 구성을 클릭합니다. 여기서는 애플리케이션 이름과 이메일만 입력하면 됩니다.
동의 화면 구성이 완료되면 사용자 인증 정보 만들기 버튼을 클릭하고, OAuth 클라이언트 ID를 선택합니다.
애플리케이션 유형은 웹 애플리케이션을 선택합니다.
승인된 리디렉션 URI에 http://localhost (테스트용 로컬 서버) 또는 실제 서버 URI (예: https://8440.co.kr/drive/index.php)를 추가합니다.
만들기 버튼을 클릭하면 클라이언트 ID와 클라이언트 Secret이 생성됩니다.
3. OAuth 2.0 클라이언트 ID와 Secret을 PHP 코드에 적용
Google에서 발급한 클라이언트 ID와 클라이언트 Secret을 PHP 코드에 적용하고, 인증 URL을 통해 권한을 부여받습니다.
<?php
require_once 'vendor/autoload.php';
session_start();
// Google 클라이언트 설정
$client = new Google_Client();
$client->setClientId('YOUR_CLIENT_ID');
$client->setClientSecret('YOUR_CLIENT_SECRET');
$client->setRedirectUri('YOUR_REDIRECT_URI'); // 예: 'https://8440.co.kr/drive/index.php'
$client->addScope(Google_Service_Drive::DRIVE);
// 세션에 저장된 토큰이 없다면 인증 URL 생성
if (!isset($_SESSION['access_token'])) {
$authUrl = $client->createAuthUrl();
echo "<a href='$authUrl'>Google Drive 인증</a>";
exit;
}
// 인증 코드가 전달되면 액세스 토큰 발급 및 저장
if (isset($_GET['code'])) {
$client->authenticate($_GET['code']);
$_SESSION['access_token'] = $client->getAccessToken();
header('Location: ' . filter_var($client->getRedirectUri(), FILTER_SANITIZE_URL));
exit;
}
// Google Drive 서비스 초기화
$service = new Google_Service_Drive($client);
echo "Google Drive에 연결되었습니다!";
?>
위 코드에서:
YOUR_CLIENT_ID, YOUR_CLIENT_SECRET, YOUR_REDIRECT_URI를 Google Cloud Console에서 얻은 값으로 교체합니다.
4. 브라우저에서 인증 실행
웹 서버에서 위 PHP 파일을 실행합니다.
Google Drive 인증 링크를 클릭하면 Google 로그인 페이지로 이동하게 됩니다.
권한을 승인하면 액세스 토큰이 세션에 저장됩니다.
5. 인증 완료 후 Google Drive API 사용
이제 인증이 완료되었고, Google Drive에 접근할 수 있는 토큰이 세션에 저장되어 있습니다. 이후 코드를 추가하여 파일을 업로드하거나 관리할 수 있습니다.
이 과정을 통해 Google Cloud Console에서 설정한 클라이언트 ID와 Secret을 이용해 PHP에서 OAuth 2.0 인증을 한 번 수행하고, 인증 토큰을 세션에 저장하여 재사용할 수 있습니다.
Tip: 설정 과정에서 문제가 계속 발생할 경우, 설정이 복잡한 부분을 도와드릴 수 있습니다.
나의 말:
<?php
require_once $_SERVER['DOCUMENT_ROOT'] . '/vendor/autoload.php';
session_start();
// Google OAuth2 인증 설정
$client = new Google_Client();
$client->setClientId('201614692575-nbik0u921jg5826f4e9j22pd6mfbmuhr.apps.googleusercontent.com');
$client->setClientSecret('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');
$client->setRedirectUri('https://8440.co.kr/drive/index.php'); // 리디렉션 URI
$client->addScope(Google_Service_Drive::DRIVE);
// 세션에 저장된 액세스 토큰이 있는지 확인
if (isset($_SESSION['access_token']) && $_SESSION['access_token']) {
$client->setAccessToken($_SESSION['access_token']);
} else {
// 액세스 토큰이 없으면 인증 URL 생성 및 표시
$authUrl = $client->createAuthUrl();
echo "<a href='$authUrl'>구글 드라이브 인증</a>";
exit;
}
// 인증 코드가 전달된 경우 액세스 토큰을 요청하고 세션에 저장
if (isset($_GET['code'])) {
$client->authenticate($_GET['code']);
$_SESSION['access_token'] = $client->getAccessToken();
// 디버깅용: 액세스 토큰이 제대로 저장되었는지 확인
var_dump($_SESSION['access_token']); // 토큰 정보 확인
header('Location: ' . filter_var($client->getRedirectUri(), FILTER_SANITIZE_URL));
exit;
}
// Google Drive 서비스 초기화
$service = new Google_Service_Drive($client);
try {
// '미래기업' 폴더가 이미 있는지 확인하고 없으면 생성
$folderName = '미래기업';
$folderId = null;
// 폴더 검색
$response = $service->files->listFiles(array(
'q' => "name='$folderName' and mimeType='application/vnd.google-apps.folder' and trashed=false",
'spaces' => 'drive',
'fields' => 'files(id, name)',
));
// 폴더가 존재할 경우, 폴더 ID를 사용하고 없을 경우 새 폴더 생성
if (count($response->files) > 0) {
$folderId = $response->files[0]->id;
} else {
// 폴더가 없는 경우 생성
$folderMetadata = new Google_Service_Drive_DriveFile(array(
'name' => $folderName,
'mimeType' => 'application/vnd.google-apps.folder'
));
$folder = $service->files->create($folderMetadata, array(
'fields' => 'id'
));
$folderId = $folder->id;
echo "폴더 '미래기업'이 생성되었습니다. 폴더 ID: " . $folderId . "<br>";
}
// 업로드할 파일 설정
$filePath = $_SERVER['DOCUMENT_ROOT'] . '/path/to/your/file.pdf'; // 업로드할 파일의 실제 경로
$fileName = 'example_file.pdf'; // 구글 드라이브에 저장될 파일 이름
// 파일 메타데이터 및 업로드 실행
$fileMetadata = new Google_Service_Drive_DriveFile(array(
'name' => $fileName,
'parents' => array($folderId)
));
$content = file_get_contents($filePath);
$uploadedFile = $service->files->create($fileMetadata, array(
'data' => $content,
'mimeType' => mime_content_type($filePath),
'uploadType' => 'multipart',
'fields' => 'id'
));
// 모든 사용자가 볼 수 있도록 파일 권한 설정
$permission = new Google_Service_Drive_Permission(array(
'type' => 'anyone',
'role' => 'reader' // 읽기 권한
));
$service->permissions->create($uploadedFile->id, $permission);
echo "파일이 구글 드라이브의 '미래기업' 폴더에 업로드되었고, 모든 사용자가 접근할 수 있도록 설정되었습니다. 파일 ID: " . $uploadedFile->id;
} catch (Exception $e) {
echo '오류 발생: ' . $e->getMessage();
}
?>
위의 파일에서 구글 드라이브 인증을 받으면 그 토큰을 /tokens/token.json으로 저장하는 로직도 추가해줘.
ChatGPT의 말:
ChatGPT
아래 코드에서는 OAuth 인증 후 발급받은 액세스 토큰을 /tokens/token.json 파일에 저장하는 로직이 추가되었습니다. 이렇게 저장된 토큰 파일을 통해 재인증 없이 Google Drive API에 접근할 수 있습니다.
수정된 전체 코드:
<?php
require_once $_SERVER['DOCUMENT_ROOT'] . '/vendor/autoload.php';
session_start();
// Google OAuth2 클라이언트 설정
$client = new Google_Client();
$client->setClientId('201614692575-nbik0u921jg5826f4e9j22pd6mfbmuhr.apps.googleusercontent.com');
$client->setClientSecret('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');
$client->setRedirectUri('https://8440.co.kr/drive/index.php'); // 리디렉션 URI
$client->addScope(Google_Service_Drive::DRIVE);
// 토큰 파일 경로 설정
$tokenFile = $_SERVER['DOCUMENT_ROOT'] . '/tokens/token.json';
// 토큰 파일이 존재하는지 확인
if (file_exists($tokenFile)) {
// 파일에서 액세스 토큰을 읽어와 설정
$accessToken = json_decode(file_get_contents($tokenFile), true);
$client->setAccessToken($accessToken);
// 만약 토큰이 만료되었으면 리프레시 토큰을 사용해 갱신하고 파일에 다시 저장
if ($client->isAccessTokenExpired()) {
$client->fetchAccessTokenWithRefreshToken($client->getRefreshToken());
file_put_contents($tokenFile, json_encode($client->getAccessToken()));
}
} else {
// 액세스 토큰이 없으면 인증 URL 생성 및 표시
if (!isset($_GET['code'])) {
$authUrl = $client->createAuthUrl();
echo "<a href='$authUrl'>구글 드라이브 인증</a>";
exit;
} else {
// 사용자가 인증을 완료하고 돌아오면 액세스 토큰을 받아서 파일에 저장
$client->authenticate($_GET['code']);
$accessToken = $client->getAccessToken();
// 새로 발급받은 토큰을 파일에 저장
if (!file_exists(dirname($tokenFile))) {
mkdir(dirname($tokenFile), 0700, true); // 디렉터리가 없으면 생성
}
file_put_contents($tokenFile, json_encode($accessToken));
header('Location: ' . filter_var($client->getRedirectUri(), FILTER_SANITIZE_URL));
exit;
}
}
// Google Drive 서비스 초기화
$service = new Google_Service_Drive($client);
try {
// '미래기업' 폴더가 이미 있는지 확인하고 없으면 생성
$folderName = '미래기업';
$folderId = null;
// 폴더 검색
$response = $service->files->listFiles(array(
'q' => "name='$folderName' and mimeType='application/vnd.google-apps.folder' and trashed=false",
'spaces' => 'drive',
'fields' => 'files(id, name)',
));
// 폴더가 존재할 경우, 폴더 ID를 사용하고 없을 경우 새 폴더 생성
if (count($response->files) > 0) {
$folderId = $response->files[0]->id;
} else {
// 폴더가 없는 경우 생성
$folderMetadata = new Google_Service_Drive_DriveFile(array(
'name' => $folderName,
'mimeType' => 'application/vnd.google-apps.folder'
));
$folder = $service->files->create($folderMetadata, array(
'fields' => 'id'
));
$folderId = $folder->id;
echo "폴더 '미래기업'이 생성되었습니다. 폴더 ID: " . $folderId . "<br>";
}
// 업로드할 파일 설정
$filePath = $_SERVER['DOCUMENT_ROOT'] . '/path/to/your/file.pdf'; // 업로드할 파일의 실제 경로
$fileName = 'example_file.pdf'; // 구글 드라이브에 저장될 파일 이름
// 파일 메타데이터 및 업로드 실행
$fileMetadata = new Google_Service_Drive_DriveFile(array(
'name' => $fileName,
'parents' => array($folderId)
));
$content = file_get_contents($filePath);
$uploadedFile = $service->files->create($fileMetadata, array(
'data' => $content,
'mimeType' => mime_content_type($filePath),
'uploadType' => 'multipart',
'fields' => 'id'
));
// 모든 사용자가 볼 수 있도록 파일 권한 설정
$permission = new Google_Service_Drive_Permission(array(
'type' => 'anyone',
'role' => 'reader' // 읽기 권한
));
$service->permissions->create($uploadedFile->id, $permission);
echo "파일이 구글 드라이브의 '미래기업' 폴더에 업로드되었고, 모든 사용자가 접근할 수 있도록 설정되었습니다. 파일 ID: " . $uploadedFile->id;
} catch (Exception $e) {
echo '오류 발생: ' . $e->getMessage();
}
?>
추가된 내용 설명
토큰 파일 경로 설정:
token.json 파일을 저장할 경로로 $_SERVER['DOCUMENT_ROOT'] . '/tokens/token.json'을 설정합니다.
토큰 파일에 저장 로직 추가:
새로운 액세스 토큰을 발급받은 후, file_put_contents()를 통해 token.json 파일에 저장합니다.
mkdir()로 tokens 폴더가 없으면 생성하도록 했습니다.
토큰 파일에서 읽기 및 갱신:
token.json 파일이 존재하고, 만료되지 않은 토큰이 있다면 이를 사용합니다.
만약 토큰이 만료된 경우, 리프레시 토큰을 통해 갱신하고, 새로운 토큰으로 파일을 덮어씁니다.
동작 흐름
처음 한 번 Google 인증을 완료하면 토큰이 token.json 파일에 저장됩니다.
이후에는 이 파일에 저장된 토큰을 사용해 다시 인증할 필요 없이 Google Drive API에 접근할 수 있습니다.
나의 말:
위에서 업로드된 구글 드라이브 파일을
https://drive.google.com/drive/home
여기서 볼 수 있는것인가요?
ChatGPT의 말:
ChatGPT
https://drive.google.com/drive/home에서 업로드된 파일을 바로 확인할 수는 없습니다. API를 통해 업로드된 파일은 기본적으로 Google Drive의 루트 디렉토리 또는 지정된 폴더에 저장됩니다.
업로드한 파일을 찾는 방법
**Google Drive의 "내 드라이브"**에 접속한 후, 상단의 검색 창을 사용하여 파일 이름이나 파일 ID로 검색할 수 있습니다.
코드에서 특정 폴더 ID를 지정했다면, 해당 폴더에서 업로드한 파일을 찾을 수 있습니다.
API로 업로드한 파일을 쉽게 찾을 수 있도록 하는 방법
폴더 ID를 명확하게 설정하여 특정 폴더에 파일을 업로드하도록 하면 파일 관리를 더 쉽게 할 수 있습니다.
업로드 후 생성된 파일 ID를 저장하거나 기록해 두면, URL 형식으로https://drive.google.com/file/d/[파일 ID]을 사용하여 파일에 직접 접근할 수 있습니다.
즉, API로 업로드한 파일은 Google Drive 웹 인터페이스에서도 검색을 통해 확인할 수 있지만, 기본 경로에 표시되지는 않을 수 있습니다.
나의 말:
api로 업로드된 폴더 및 파일을 보려면 어떻게 해야 하나요?
ChatGPT의 말:
ChatGPT
Google Drive API를 사용하여 API로 업로드된 폴더와 파일을 확인하려면 Google Drive API의 파일 리스트 기능을 활용할 수 있습니다. 이를 통해 특정 폴더 안의 파일 목록을 가져오거나, 파일과 폴더의 이름을 기준으로 검색할 수 있습니다.
1. Google Drive API를 통해 특정 폴더의 파일 및 하위 폴더 확인하기
아래는 Google Drive API를 통해 특정 폴더 안의 파일과 하위 폴더 목록을 가져오는 코드 예시입니다.
<?php
require_once $_SERVER['DOCUMENT_ROOT'] . '/vendor/autoload.php';
session_start();
// Google OAuth2 클라이언트 설정
$client = new Google_Client();
$client->setClientId('YOUR_CLIENT_ID');
$client->setClientSecret('YOUR_CLIENT_SECRET');
$client->setRedirectUri('YOUR_REDIRECT_URI');
$client->addScope(Google_Service_Drive::DRIVE);
// 세션에 저장된 토큰 확인 및 설정
$tokenFile = $_SERVER['DOCUMENT_ROOT'] . '/tokens/token.json';
if (file_exists($tokenFile)) {
$accessToken = json_decode(file_get_contents($tokenFile), true);
$client->setAccessToken($accessToken);
if ($client->isAccessTokenExpired()) {
$client->fetchAccessTokenWithRefreshToken($client->getRefreshToken());
file_put_contents($tokenFile, json_encode($client->getAccessToken()));
}
} else {
echo "OAuth 인증이 필요합니다.";
exit;
}
// Google Drive 서비스 초기화
$service = new Google_Service_Drive($client);
// 폴더 ID 설정 (예: '미래기업' 폴더 ID)
$folderId = 'YOUR_FOLDER_ID'; // 확인하고자 하는 폴더의 ID를 여기에 입력
try {
// 지정된 폴더 안의 파일과 하위 폴더 목록 가져오기
$response = $service->files->listFiles([
'q' => "'$folderId' in parents and trashed=false", // 특정 폴더 안에서 삭제되지 않은 파일과 폴더 검색
'fields' => 'files(id, name, mimeType)',
]);
echo "<h2>폴더 '$folderId' 내의 파일 목록:</h2>";
foreach ($response->files as $file) {
$fileType = $file->mimeType === 'application/vnd.google-apps.folder' ? '폴더' : '파일';
echo "$fileType 이름: " . $file->name . "<br>";
echo "$fileType ID: " . $file->id . "<br><br>";
}
} catch (Exception $e) {
echo '오류 발생: ' . $e->getMessage();
}
?>
코드 설명
폴더 안의 파일과 하위 폴더 검색:
q 매개변수를 사용해 '폴더 ID' in parents 조건으로 특정 폴더 안의 파일과 하위 폴더를 검색합니다.
trashed=false 조건은 휴지통에 들어가지 않은 파일만 가져옵니다.
파일과 폴더의 정보 출력:
files(id, name, mimeType) 필드를 사용하여 **파일 ID, 이름, 타입(파일 또는 폴더)**을 가져옵니다.
mimeType이 'application/vnd.google-apps.folder'인 경우, 해당 항목이 폴더임을 의미합니다.
폴더 ID 설정:
folderId에 검색하고자 하는 폴더의 ID를 설정합니다. 특정 폴더의 ID는 Google Drive 웹에서 해당 폴더를 열고 URL에서 확인할 수 있습니다.
참고
루트 폴더의 파일 목록을 가져오고자 한다면, folderId에 "root"를 지정할 수 있습니다.
직접 접근 링크를 만들려면 파일 ID를 사용해 https://drive.google.com/file/d/[파일 ID] 형식의 링크를 구성할 수 있습니다.
이 코드를 통해 Google Drive API를 사용하여 특정 폴더 내의 파일 및 폴더를 프로그램적으로 검색하고 관리할 수 있습니다.
나의 말:
구글 console에서 보는 방법은?
ChatGPT의 말:
ChatGPT
Google Console에서 Google Drive API로 업로드된 파일을 직접 확인하는 기능은 제공되지 않습니다. Google Console은 API를 관리하고 설정하는 곳으로, Google Drive에 저장된 파일을 확인하거나 관리하는 기능은 없습니다. 대신, Google Drive 웹사이트에서 파일을 확인할 수 있습니다.
Google Drive 웹사이트에서 API로 업로드된 파일 및 폴더 확인하기
API로 업로드된 파일은 Google Drive 웹사이트에서 찾을 수 있으며, API를 통해 특정 폴더에 업로드했다면 그 폴더 경로에서 파일을 검색할 수 있습니다.
Google Drive 웹사이트에 로그인합니다: https://drive.google.com/
"내 드라이브" 또는 **"공유 드라이브"**에서 파일을 확인할 수 있습니다.
API로 특정 폴더에 업로드했다면, 해당 폴더를 찾아 들어가면 파일이 보일 것입니다.
검색 기능 사용:
상단의 검색 창에서 파일 이름이나 파일 유형(예: PDF, 이미지 등)으로 검색하여 API로 업로드한 파일을 찾을 수 있습니다.
파일 ID로 검색:
Google Drive URL 형식 ( https://drive.google.com/file/d/[파일 ID])을 사용하여 파일 ID를 직접 입력하면 해당 파일에 접근할 수 있습니다.
참고: Google Drive API에서 파일 및 폴더를 관리하는 Google Cloud Console 기능은 없음
Google Cloud Console은 API 설정, 권한 관리, API 키 관리 등을 위한 도구입니다.
파일이나 폴더의 콘텐츠는 Google Drive 웹사이트나 API를 통해서만 접근하고 확인할 수 있습니다.
나의 말:
<?php
require_once $_SERVER['DOCUMENT_ROOT'] . '/vendor/autoload.php';
session_start();
// Google OAuth2 클라이언트 설정
$client = new Google_Client();
$client->setClientId('201614692575-nbik0u921jg5826f4e9j22pd6mfbmuhr.apps.googleusercontent.com');
$client->setClientSecret('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');
$client->setRedirectUri('https://8440.co.kr/drive/index.php'); // 리디렉션 URI
$client->addScope(Google_Service_Drive::DRIVE);
// 토큰 파일 경로 설정
$tokenFile = $_SERVER['DOCUMENT_ROOT'] . '/tokens/token.json';
// 토큰 파일이 존재하는지 확인
if (file_exists($tokenFile)) {
// 파일에서 액세스 토큰을 읽어와 설정
$accessToken = json_decode(file_get_contents($tokenFile), true);
$client->setAccessToken($accessToken);
// 만약 토큰이 만료되었으면 리프레시 토큰을 사용해 갱신하고 파일에 다시 저장
if ($client->isAccessTokenExpired()) {
$client->fetchAccessTokenWithRefreshToken($client->getRefreshToken());
file_put_contents($tokenFile, json_encode($client->getAccessToken()));
}
} else {
// 액세스 토큰이 없으면 인증 URL 생성 및 표시
if (!isset($_GET['code'])) {
$authUrl = $client->createAuthUrl();
echo "<a href='$authUrl'>구글 드라이브 인증</a>";
exit;
} else {
// 사용자가 인증을 완료하고 돌아오면 액세스 토큰을 받아서 파일에 저장
$client->authenticate($_GET['code']);
$accessToken = $client->getAccessToken();
// 새로 발급받은 토큰을 파일에 저장
if (!file_exists(dirname($tokenFile))) {
mkdir(dirname($tokenFile), 0700, true); // 디렉터리가 없으면 생성
}
file_put_contents($tokenFile, json_encode($accessToken));
header('Location: ' . filter_var($client->getRedirectUri(), FILTER_SANITIZE_URL));
exit;
}
}
// Google Drive 서비스 초기화
$service = new Google_Service_Drive($client);
try {
// '미래기업' 폴더가 이미 있는지 확인하고 없으면 생성
$folderName = '미래기업';
$folderId = null;
// 폴더 검색
$response = $service->files->listFiles(array(
'q' => "name='$folderName' and mimeType='application/vnd.google-apps.folder' and trashed=false",
'spaces' => 'drive',
'fields' => 'files(id, name)',
));
// 폴더가 존재할 경우, 폴더 ID를 사용하고 없을 경우 새 폴더 생성
if (count($response->files) > 0) {
$folderId = $response->files[0]->id;
} else {
// 폴더가 없는 경우 생성
$folderMetadata = new Google_Service_Drive_DriveFile(array(
'name' => $folderName,
'mimeType' => 'application/vnd.google-apps.folder'
));
$folder = $service->files->create($folderMetadata, array(
'fields' => 'id'
));
$folderId = $folder->id;
echo "폴더 '미래기업'이 생성되었습니다. 폴더 ID: " . $folderId . "<br>";
}
// 업로드할 파일 설정
$filePath = $_SERVER['DOCUMENT_ROOT'] . '/index.php'; // 업로드할 파일의 실제 경로
$fileName = 'index.php'; // 구글 드라이브에 저장될 파일 이름
// 파일 메타데이터 및 업로드 실행
$fileMetadata = new Google_Service_Drive_DriveFile(array(
'name' => $fileName,
'parents' => array($folderId)
));
$content = file_get_contents($filePath);
$uploadedFile = $service->files->create($fileMetadata, array(
'data' => $content,
'mimeType' => mime_content_type($filePath),
'uploadType' => 'multipart',
'fields' => 'id'
));
// 모든 사용자가 볼 수 있도록 파일 권한 설정
$permission = new Google_Service_Drive_Permission(array(
'type' => 'anyone',
'role' => 'reader' // 읽기 권한
));
$service->permissions->create($uploadedFile->id, $permission);
echo "파일이 구글 드라이브의 '미래기업' 폴더에 업로드되었고, 모든 사용자가 접근할 수 있도록 설정되었습니다. 파일 ID: " . $uploadedFile->id;
} catch (Exception $e) {
echo '오류 발생: ' . $e->getMessage();
}
?>
위의 코드에서 토큰이 만료되면 다시 토큰을 갱신하는 코드를 추가하면?
ChatGPT의 말:
ChatGPT
위 코드에서는 이미 토큰 만료 여부를 확인하고 자동으로 갱신하는 로직이 포함되어 있습니다. 이 부분은 if ($client->isAccessTokenExpired()) 조건에서 이루어지며, 리프레시 토큰을 사용해 새 액세스 토큰을 발급받고, 이를 token.json에 저장하고 있습니다.
다시 설명드리면, 다음의 코드 부분이 토큰이 만료될 때 자동으로 갱신하는 역할을 수행합니다.
if ($client->isAccessTokenExpired()) {
$client->fetchAccessTokenWithRefreshToken($client->getRefreshToken());
file_put_contents($tokenFile, json_encode($client->getAccessToken()));
}
코드의 동작 흐름 요약
토큰 파일이 존재하는지 확인: token.json 파일이 있는 경우, 파일을 읽어 액세스 토큰을 설정합니다.
토큰 만료 여부 확인: isAccessTokenExpired() 메서드를 통해 현재 토큰이 만료되었는지 확인합니다.
만료된 경우 갱신:
fetchAccessTokenWithRefreshToken() 메서드를 사용하여 리프레시 토큰을 통해 새로운 액세스 토큰을 발급받습니다.
새로 발급받은 토큰은 token.json 파일에 덮어쓰기하여, 이후에도 최신 토큰이 저장되도록 합니다.
코드 전체 요약
위의 전체 코드에는 이미 만료된 토큰을 갱신하고, 새로운 액세스 토큰을 파일에 저장하는 로직이 포함되어 있습니다. 별도로 추가할 필요 없이 이 코드 자체로 자동 갱신이 이루어집니다.
나의 말:
처음실행에는 업로드가 index.php가 잘 올라갔다. 이 후 내가 이 파일을 삭제하고 다시 위의 코드를 실행하니 올라가지 않는다. 혹시 중복된 파일이 올라가지 않게 설계되어있는가?
위의 코드에서 디버그 코드를 포함해서 수정해줘.
<?php
require_once $_SERVER['DOCUMENT_ROOT'] . '/vendor/autoload.php';
session_start();
// Google OAuth2 클라이언트 설정
$client = new Google_Client();
$client->setClientId('201614692575-nbik0u921jg5826f4e9j22pd6mfbmuhr.apps.googleusercontent.com');
$client->setClientSecret('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');
$client->setRedirectUri('https://8440.co.kr/drive/index.php'); // 리디렉션 URI
$client->addScope(Google_Service_Drive::DRIVE);
// 토큰 파일 경로 설정
$tokenFile = $_SERVER['DOCUMENT_ROOT'] . '/tokens/token.json';
// 토큰 파일이 존재하는지 확인
if (file_exists($tokenFile)) {
// 파일에서 액세스 토큰을 읽어와 설정
$accessToken = json_decode(file_get_contents($tokenFile), true);
$client->setAccessToken($accessToken);
// 만약 토큰이 만료되었으면 리프레시 토큰을 사용해 갱신하고 파일에 다시 저장
if ($client->isAccessTokenExpired()) {
$client->fetchAccessTokenWithRefreshToken($client->getRefreshToken());
file_put_contents($tokenFile, json_encode($client->getAccessToken()));
}
} else {
// 액세스 토큰이 없으면 인증 URL 생성 및 표시
if (!isset($_GET['code'])) {
$authUrl = $client->createAuthUrl();
echo "<a href='$authUrl'>구글 드라이브 인증</a>";
exit;
} else {
// 사용자가 인증을 완료하고 돌아오면 액세스 토큰을 받아서 파일에 저장
$client->authenticate($_GET['code']);
$accessToken = $client->getAccessToken();
// 새로 발급받은 토큰을 파일에 저장
if (!file_exists(dirname($tokenFile))) {
mkdir(dirname($tokenFile), 0700, true); // 디렉터리가 없으면 생성
}
file_put_contents($tokenFile, json_encode($accessToken));
header('Location: ' . filter_var($client->getRedirectUri(), FILTER_SANITIZE_URL));
exit;
}
}
// Google Drive 서비스 초기화
$service = new Google_Service_Drive($client);
try {
// '미래기업' 폴더가 이미 있는지 확인하고 없으면 생성
$folderName = '미래기업';
$folderId = null;
// 폴더 검색
$response = $service->files->listFiles(array(
'q' => "name='$folderName' and mimeType='application/vnd.google-apps.folder' and trashed=false",
'spaces' => 'drive',
'fields' => 'files(id, name)',
));
// 폴더가 존재할 경우, 폴더 ID를 사용하고 없을 경우 새 폴더 생성
if (count($response->files) > 0) {
$folderId = $response->files[0]->id;
} else {
// 폴더가 없는 경우 생성
$folderMetadata = new Google_Service_Drive_DriveFile(array(
'name' => $folderName,
'mimeType' => 'application/vnd.google-apps.folder'
));
$folder = $service->files->create($folderMetadata, array(
'fields' => 'id'
));
$folderId = $folder->id;
echo "폴더 '미래기업'이 생성되었습니다. 폴더 ID: " . $folderId . "<br>";
}
// 업로드할 파일 설정
$filePath = $_SERVER['DOCUMENT_ROOT'] . '/index.php'; // 업로드할 파일의 실제 경로
$fileName = 'index.php'; // 구글 드라이브에 저장될 파일 이름
// 파일 메타데이터 및 업로드 실행
$fileMetadata = new Google_Service_Drive_DriveFile(array(
'name' => $fileName,
'parents' => array($folderId)
));
$content = file_get_contents($filePath);
$uploadedFile = $service->files->create($fileMetadata, array(
'data' => $content,
'mimeType' => mime_content_type($filePath),
'uploadType' => 'multipart',
'fields' => 'id'
));
// 모든 사용자가 볼 수 있도록 파일 권한 설정
$permission = new Google_Service_Drive_Permission(array(
'type' => 'anyone',
'role' => 'reader' // 읽기 권한
));
$service->permissions->create($uploadedFile->id, $permission);
echo "파일이 구글 드라이브의 '미래기업' 폴더에 업로드되었고, 모든 사용자가 접근할 수 있도록 설정되었습니다. 파일 ID: " . $uploadedFile->id;
} catch (Exception $e) {
echo '오류 발생: ' . $e->getMessage();
}
?>
ChatGPT의 말:
ChatGPT
파일이 Google Drive에 다시 업로드되지 않는 문제를 해결하기 위해, 중복 파일이 있는지 확인한 후, 중복 파일이 있을 경우 기존 파일을 삭제하거나 다른 이름으로 업로드하는 방법을 사용할 수 있습니다. 또한, 디버그 메시지를 추가하여 업로드 진행 상황과 오류 메시지를 확인할 수 있습니다.
아래 코드는 index.php 파일이 중복되어 있는지 확인하고, 중복된 파일이 있으면 삭제 후 새 파일을 업로드합니다. 또한, 각 단계에 디버그 메시지를 추가하여 문제를 쉽게 파악할 수 있도록 했습니다.
<?php
require_once $_SERVER['DOCUMENT_ROOT'] . '/vendor/autoload.php';
session_start();
// Google OAuth2 클라이언트 설정
$client = new Google_Client();
$client->setClientId('201614692575-nbik0u921jg5826f4e9j22pd6mfbmuhr.apps.googleusercontent.com');
$client->setClientSecret('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');
$client->setRedirectUri('https://8440.co.kr/drive/index.php');
$client->addScope(Google_Service_Drive::DRIVE);
// 토큰 파일 경로 설정
$tokenFile = $_SERVER['DOCUMENT_ROOT'] . '/tokens/token.json';
if (file_exists($tokenFile)) {
$accessToken = json_decode(file_get_contents($tokenFile), true);
$client->setAccessToken($accessToken);
if ($client->isAccessTokenExpired()) {
$client->fetchAccessTokenWithRefreshToken($client->getRefreshToken());
file_put_contents($tokenFile, json_encode($client->getAccessToken()));
}
} else {
if (!isset($_GET['code'])) {
$authUrl = $client->createAuthUrl();
echo "<a href='$authUrl'>구글 드라이브 인증</a>";
exit;
} else {
$client->authenticate($_GET['code']);
$accessToken = $client->getAccessToken();
if (!file_exists(dirname($tokenFile))) {
mkdir(dirname($tokenFile), 0700, true);
}
file_put_contents($tokenFile, json_encode($accessToken));
header('Location: ' . filter_var($client->getRedirectUri(), FILTER_SANITIZE_URL));
exit;
}
}
// Google Drive 서비스 초기화
$service = new Google_Service_Drive($client);
try {
// '미래기업' 폴더가 있는지 확인하고 없으면 생성
$folderName = '미래기업';
$folderId = null;
$response = $service->files->listFiles([
'q' => "name='$folderName' and mimeType='application/vnd.google-apps.folder' and trashed=false",
'spaces' => 'drive',
'fields' => 'files(id, name)',
]);
if (count($response->files) > 0) {
$folderId = $response->files[0]->id;
} else {
$folderMetadata = new Google_Service_Drive_DriveFile([
'name' => $folderName,
'mimeType' => 'application/vnd.google-apps.folder'
]);
$folder = $service->files->create($folderMetadata, ['fields' => 'id']);
$folderId = $folder->id;
echo "폴더 '미래기업'이 생성되었습니다. 폴더 ID: " . $folderId . "<br>";
}
// 파일 업로드 전에 동일한 이름의 파일이 있는지 확인
$filePath = $_SERVER['DOCUMENT_ROOT'] . '/index.php';
$fileName = 'index.php';
$existingFiles = $service->files->listFiles([
'q' => "name='$fileName' and '$folderId' in parents and trashed=false",
'spaces' => 'drive',
'fields' => 'files(id, name)',
]);
// 동일한 이름의 파일이 있으면 삭제
if (count($existingFiles->files) > 0) {
foreach ($existingFiles->files as $existingFile) {
$service->files->delete($existingFile->id);
echo "기존 파일 '" . $existingFile->name . "'이 삭제되었습니다.<br>";
}
}
// 파일 메타데이터 및 업로드 실행
$fileMetadata = new Google_Service_Drive_DriveFile([
'name' => $fileName,
'parents' => [$folderId]
]);
$content = file_get_contents($filePath);
$uploadedFile = $service->files->create($fileMetadata, [
'data' => $content,
'mimeType' => mime_content_type($filePath),
'uploadType' => 'multipart',
'fields' => 'id'
]);
// 모든 사용자가 볼 수 있도록 파일 권한 설정
$permission = new Google_Service_Drive_Permission([
'type' => 'anyone',
'role' => 'reader'
]);
$service->permissions->create($uploadedFile->id, $permission);
echo "파일이 구글 드라이브의 '미래기업' 폴더에 업로드되었고, 모든 사용자가 접근할 수 있도록 설정되었습니다. 파일 ID: " . $uploadedFile->id;
} catch (Exception $e) {
echo '오류 발생: ' . $e->getMessage();
}
?>
수정된 부분 요약
중복 파일 확인 및 삭제:
listFiles 메서드를 사용하여 미래기업 폴더 내 동일한 이름의 파일이 있는지 확인합니다.
동일한 이름의 파일이 있는 경우, delete 메서드를 사용하여 기존 파일을 삭제합니다.
디버그 메시지 추가:
중복 파일이 발견되어 삭제될 때 메시지를 출력합니다.
업로드 성공 여부 및 단계별 상태를 쉽게 확인할 수 있도록 각 주요 단계에 echo를 통해 디버그 메시지를 추가했습니다.
주요 디버그 포인트
폴더 생성 또는 중복 폴더 확인
기존 파일이 삭제되었는지 여부
파일 업로드 성공 여부 및 파일 ID 출력
이제 중복 파일이 있을 경우 기존 파일을 자동으로 삭제하고 새 파일을 업로드할 수 있습니다. 각 단계의 상태를 확인하는 디버그 메시지를 통해 문제 발생 시 원인을 쉽게 파악할 수 있습니다.
나의 말:
view.php파일에 위의 저장된 파일 리스트를 보는 코드를 만들어줘.
ChatGPT의 말:
ChatGPT
아래 코드는 Google Drive API를 사용하여 특정 폴더 내에 있는 파일 목록을 표시하는 view.php 파일 예제입니다. 이 코드는 미래기업 폴더에 저장된 파일 목록을 가져와 화면에 표시합니다.
view.php 파일 코드
<?php
require_once $_SERVER['DOCUMENT_ROOT'] . '/vendor/autoload.php';
session_start();
// Google OAuth2 클라이언트 설정
$client = new Google_Client();
$client->setClientId('201614692575-nbik0u921jg5826f4e9j22pd6mfbmuhr.apps.googleusercontent.com');
$client->setClientSecret('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');
$client->setRedirectUri('https://8440.co.kr/drive/view.php'); // 리디렉션 URI
$client->addScope(Google_Service_Drive::DRIVE);
// 토큰 파일 경로 설정
$tokenFile = $_SERVER['DOCUMENT_ROOT'] . '/tokens/token.json';
if (file_exists($tokenFile)) {
$accessToken = json_decode(file_get_contents($tokenFile), true);
$client->setAccessToken($accessToken);
if ($client->isAccessTokenExpired()) {
$client->fetchAccessTokenWithRefreshToken($client->getRefreshToken());
file_put_contents($tokenFile, json_encode($client->getAccessToken()));
}
} else {
if (!isset($_GET['code'])) {
$authUrl = $client->createAuthUrl();
echo "<a href='$authUrl'>구글 드라이브 인증</a>";
exit;
} else {
$client->authenticate($_GET['code']);
$accessToken = $client->getAccessToken();
if (!file_exists(dirname($tokenFile))) {
mkdir(dirname($tokenFile), 0700, true);
}
file_put_contents($tokenFile, json_encode($accessToken));
header('Location: ' . filter_var($client->getRedirectUri(), FILTER_SANITIZE_URL));
exit;
}
}
// Google Drive 서비스 초기화
$service = new Google_Service_Drive($client);
try {
// '미래기업' 폴더 ID 가져오기
$folderName = '미래기업';
$folderId = null;
// '미래기업' 폴더 검색
$response = $service->files->listFiles([
'q' => "name='$folderName' and mimeType='application/vnd.google-apps.folder' and trashed=false",
'spaces' => 'drive',
'fields' => 'files(id, name)',
]);
if (count($response->files) > 0) {
$folderId = $response->files[0]->id;
} else {
echo "폴더 '미래기업'이 존재하지 않습니다.";
exit;
}
// '미래기업' 폴더 내의 파일 목록 가져오기
$files = $service->files->listFiles([
'q' => "'$folderId' in parents and trashed=false",
'spaces' => 'drive',
'fields' => 'files(id, name, mimeType, createdTime, webViewLink)',
]);
echo "<h2>'미래기업' 폴더 내의 파일 목록:</h2>";
echo "<ul>";
if (count($files->files) > 0) {
foreach ($files->files as $file) {
$fileType = $file->mimeType === 'application/vnd.google-apps.folder' ? '폴더' : '파일';
echo "<li>";
echo "$fileType: <a href='" . $file->webViewLink . "' target='_blank'>" . $file->name . "</a><br>";
echo "파일 ID: " . $file->id . "<br>";
echo "생성 시간: " . $file->createdTime . "<br><br>";
echo "</li>";
}
} else {
echo "<li>폴더에 파일이 없습니다.</li>";
}
echo "</ul>";
} catch (Exception $e) {
echo '오류 발생: ' . $e->getMessage();
}
?>
코드 설명
Google Drive API 클라이언트 설정:
client_id, client_secret, redirect_uri를 설정하고, token.json에서 액세스 토큰을 로드하여 API 접근을 설정합니다.
토큰이 만료되면 자동으로 갱신하여 token.json에 저장합니다.
폴더 ID 가져오기:
'미래기업' 폴더를 검색하여 해당 폴더의 폴더 ID를 가져옵니다. 이 ID를 통해 해당 폴더 내의 파일을 확인할 수 있습니다.
폴더 내 파일 목록 가져오기:
'미래기업' 폴더 안에 있는 파일을 listFiles 메서드로 가져옵니다.
파일의 ID, 이름, 생성 시간, 웹 링크 등을 가져와 화면에 표시합니다.
출력 형식:
파일 ID, 파일 이름, 생성 시간, 파일 링크를 HTML로 출력하여 파일 이름을 클릭하면 Google Drive에서 해당 파일로 직접 이동할 수 있습니다.
주요 사항
웹 링크 (webViewLink)를 사용하여, 파일 이름을 클릭하면 Google Drive에서 파일을 열 수 있는 링크가 표시됩니다.
폴더가 없는 경우에는 해당 폴더가 없다는 메시지를 출력합니다.
오류가 발생하면 Exception 메시지를 출력하여 디버깅에 도움을 줍니다.
이 코드를 통해 Google Drive의 '미래기업' 폴더 내 파일을 웹 페이지에서 쉽게 확인할 수 있습니다.
나의 말:
내가 구글 아이디를 2개 가지고 있는데,
이것이 전화번호도 다르고 명의도 다른데,
'미래기업'이란 폴더가 예전의 아이디의 구글드라이브의 폴더의 내용을 가져온다.
분명 project의 코드가 다른데 이런 경우는 이상하네.
ChatGPT의 말:
ChatGPT
Google Drive API로 작업할 때 다른 Google 계정으로 생성된 프로젝트에 접근하는 문제는 보통 OAuth 인증 과정에서 사용된 계정과 관련이 있습니다. 특히 두 개의 Google 계정을 가지고 있을 때, 어떤 계정으로 인증을 진행하느냐에 따라 접근하는 Google Drive의 데이터가 달라질 수 있습니다.
확인 및 해결 방법
OAuth 인증을 다시 수행하기
token.json 파일을 삭제하여 OAuth 인증을 새로 시작해보세요. 이렇게 하면, API에서 새로운 계정으로 다시 로그인하여 인증을 진행하도록 요청합니다.
이렇게 하면 현재 로그인된 Google 계정을 사용하여 '미래기업' 폴더를 가져오게 됩니다.
로그인 상태 확인
브라우저에서 인증을 진행할 때, 이전 Google 계정으로 자동 로그인될 수 있습니다.
인증을 진행하기 전 현재 Google 계정 로그인을 확인하고, 문제가 발생한 경우 브라우저에서 로그아웃 후 필요한 계정으로 다시 로그인해 보세요.
Google Console에서 올바른 프로젝트 확인
Google Console에 로그인할 때 다른 Google 계정으로 로그인한 경우 프로젝트가 다를 수 있습니다. Google Console에서도 올바른 계정으로 로그인하여 필요한 프로젝트가 설정되어 있는지 확인합니다.
예시
다시 한 번 token.json을 삭제한 후에 코드를 실행하면, 새롭게 인증 창이 뜨며 원하는 계정으로 Google Drive 폴더를 확인할 수 있습니다.
나의 말:
이렇게 하니까 잘 된다. 이제 8440.co.kr의 기존 저장장소에 있던 파일들이
/imgwork에 올려있다.
이걸 구글 드라이브에 전체 복사한 후 이제는 api로 그 파일을 참조할 수 있는것인가?
ChatGPT의 말:
ChatGPT
네, 가능합니다! 이제 /imgwork에 있는 파일들을 Google Drive에 업로드하여 참조할 수 있습니다. Google Drive API를 사용하여 이 파일들을 Google Drive로 옮기고, Google Drive의 파일 링크를 통해 파일을 참조할 수 있습니다. 아래는 해당 파일을 일괄 업로드하고, 파일 링크를 받아오는 과정입니다.
Google Drive로 파일 일괄 업로드 및 링크 참조 코드 예제
폴더 생성:
먼저 Google Drive에 /imgwork 폴더를 생성하거나, 이미 만들어둔 폴더 ID를 설정합니다.
파일 업로드 및 링크 참조 코드 작성:
/imgwork에 있는 모든 파일을 읽어 Google Drive에 업로드하고, 업로드된 파일의 링크를 저장할 수 있습니다.
<?php
require_once $_SERVER['DOCUMENT_ROOT'] . '/vendor/autoload.php';
session_start();
// Google OAuth2 클라이언트 설정
$client = new Google_Client();
$client->setClientId('YOUR_CLIENT_ID');
$client->setClientSecret('YOUR_CLIENT_SECRET');
$client->setRedirectUri('https://8440.co.kr/drive/upload.php'); // 리디렉션 URI
$client->addScope(Google_Service_Drive::DRIVE);
// 토큰 파일 경로 설정
$tokenFile = $_SERVER['DOCUMENT_ROOT'] . '/tokens/token.json';
if (file_exists($tokenFile)) {
$accessToken = json_decode(file_get_contents($tokenFile), true);
$client->setAccessToken($accessToken);
if ($client->isAccessTokenExpired()) {
$client->fetchAccessTokenWithRefreshToken($client->getRefreshToken());
file_put_contents($tokenFile, json_encode($client->getAccessToken()));
}
} else {
if (!isset($_GET['code'])) {
$authUrl = $client->createAuthUrl();
echo "<a href='$authUrl'>구글 드라이브 인증</a>";
exit;
} else {
$client->authenticate($_GET['code']);
$accessToken = $client->getAccessToken();
if (!file_exists(dirname($tokenFile))) {
mkdir(dirname($tokenFile), 0700, true);
}
file_put_contents($tokenFile, json_encode($accessToken));
header('Location: ' . filter_var($client->getRedirectUri(), FILTER_SANITIZE_URL));
exit;
}
}
// Google Drive 서비스 초기화
$service = new Google_Service_Drive($client);
// Google Drive에서 저장할 'imgwork' 폴더 ID 설정
$driveFolderId = 'YOUR_GOOGLE_DRIVE_FOLDER_ID'; // Google Drive에 미리 생성한 'imgwork' 폴더의 ID를 설정
// /imgwork 폴더에서 모든 파일을 읽어서 Google Drive로 업로드
$imgworkPath = $_SERVER['DOCUMENT_ROOT'] . '/imgwork';
$files = scandir($imgworkPath);
foreach ($files as $file) {
if ($file === '.' || $file === '..') continue; // 현재 및 상위 디렉토리 무시
$filePath = "$imgworkPath/$file";
$mimeType = mime_content_type($filePath);
// Google Drive 파일 메타데이터 설정
$fileMetadata = new Google_Service_Drive_DriveFile([
'name' => $file,
'parents' => [$driveFolderId]
]);
$content = file_get_contents($filePath);
// Google Drive에 파일 업로드
try {
$uploadedFile = $service->files->create($fileMetadata, [
'data' => $content,
'mimeType' => $mimeType,
'uploadType' => 'multipart',
'fields' => 'id, webViewLink'
]);
// 모든 사용자가 볼 수 있도록 파일 권한 설정
$permission = new Google_Service_Drive_Permission([
'type' => 'anyone',
'role' => 'reader'
]);
$service->permissions->create($uploadedFile->id, $permission);
echo "파일 '{$file}'이 업로드되었습니다. 링크: <a href='" . $uploadedFile->webViewLink . "' target='_blank'>보기</a><br>";
} catch (Exception $e) {
echo "파일 '{$file}' 업로드 중 오류 발생: " . $e->getMessage() . "<br>";
}
}
?>
코드 설명
폴더 경로 설정:
Google Drive의 imgwork 폴더 ID를 설정하여 모든 파일이 해당 폴더에 업로드되도록 지정합니다.
파일 업로드:
/imgwork 폴더의 모든 파일을 스캔하여 Google Drive에 업로드하고, 업로드 후 모든 사용자에게 읽기 권한을 부여하여 직접 링크로 파일을 참조할 수 있습니다.
파일 링크 출력:
업로드된 각 파일의 Google Drive 링크를 출력하여, 링크를 통해 파일을 웹에서 직접 참조할 수 있습니다.
이 코드를 통해 /imgwork의 파일들을 일괄적으로 Google Drive에 업로드하고, 파일 링크를 생성하여 API로 참조할 수 있게 설정할 수 있습니다.
나의 말:
위의 코드를 아래의 코드를 기반으로 실제적으로 수정해줘.
<?php
require_once $_SERVER['DOCUMENT_ROOT'] . '/vendor/autoload.php';
session_start();
// Google OAuth2 클라이언트 설정
$client = new Google_Client();
$client->setClientId('201614692575-nbik0u921jg5826f4e9j22pd6mfbmuhr.apps.googleusercontent.com');
$client->setClientSecret('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');
$client->setRedirectUri('https://8440.co.kr/drive/view.php'); // 리디렉션 URI
$client->addScope(Google_Service_Drive::DRIVE);
// 토큰 파일 경로 설정
$tokenFile = $_SERVER['DOCUMENT_ROOT'] . '/tokens/token.json';
if (file_exists($tokenFile)) {
$accessToken = json_decode(file_get_contents($tokenFile), true);
$client->setAccessToken($accessToken);
if ($client->isAccessTokenExpired()) {
$client->fetchAccessTokenWithRefreshToken($client->getRefreshToken());
file_put_contents($tokenFile, json_encode($client->getAccessToken()));
}
} else {
if (!isset($_GET['code'])) {
$authUrl = $client->createAuthUrl();
echo "<a href='$authUrl'>구글 드라이브 인증</a>";
exit;
} else {
$client->authenticate($_GET['code']);
$accessToken = $client->getAccessToken();
if (!file_exists(dirname($tokenFile))) {
mkdir(dirname($tokenFile), 0700, true);
}
file_put_contents($tokenFile, json_encode($accessToken));
header('Location: ' . filter_var($client->getRedirectUri(), FILTER_SANITIZE_URL));
exit;
}
}
// Google Drive 서비스 초기화
$service = new Google_Service_Drive($client);
try {
// '미래기업' 폴더 ID 가져오기
$folderName = '미래기업';
$folderId = null;
// '미래기업' 폴더 검색
$response = $service->files->listFiles([
'q' => "name='$folderName' and mimeType='application/vnd.google-apps.folder' and trashed=false",
'spaces' => 'drive',
'fields' => 'files(id, name)',
]);
if (count($response->files) > 0) {
$folderId = $response->files[0]->id;
} else {
echo "폴더 '미래기업'이 존재하지 않습니다.";
exit;
}
// '미래기업' 폴더 내의 파일 목록 가져오기
$files = $service->files->listFiles([
'q' => "'$folderId' in parents and trashed=false",
'spaces' => 'drive',
'fields' => 'files(id, name, mimeType, createdTime, webViewLink)',
]);
echo "<h2>'미래기업' 폴더 내의 파일 목록:</h2>";
echo "<ul>";
if (count($files->files) > 0) {
foreach ($files->files as $file) {
$fileType = $file->mimeType === 'application/vnd.google-apps.folder' ? '폴더' : '파일';
echo "<li>";
echo "$fileType: <a href='" . $file->webViewLink . "' target='_blank'>" . $file->name . "</a><br>";
echo "파일 ID: " . $file->id . "<br>";
echo "생성 시간: " . $file->createdTime . "<br><br>";
echo "</li>";
}
} else {
echo "<li>폴더에 파일이 없습니다.</li>";
}
echo "</ul>";
} catch (Exception $e) {
echo '오류 발생: ' . $e->getMessage();
}
?>
ChatGPT의 말:
ChatGPT
아래 코드는 /imgwork 디렉터리의 파일들을 Google Drive의 '미래기업' 폴더에 업로드하고, 업로드된 파일 목록을 웹 페이지에 표시하는 방식으로 기존 코드에 추가된 내용을 포함하고 있습니다.
이 코드를 통해 로컬의 /imgwork 디렉터리 파일을 Google Drive로 업로드하고, 이후 파일 링크를 생성하여 웹 페이지에서 참조할 수 있습니다.
<?php
require_once $_SERVER['DOCUMENT_ROOT'] . '/vendor/autoload.php';
session_start();
// Google OAuth2 클라이언트 설정
$client = new Google_Client();
$client->setClientId('201614692575-nbik0u921jg5826f4e9j22pd6mfbmuhr.apps.googleusercontent.com');
$client->setClientSecret('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');
$client->setRedirectUri('https://8440.co.kr/drive/view.php'); // 리디렉션 URI
$client->addScope(Google_Service_Drive::DRIVE);
// 토큰 파일 경로 설정
$tokenFile = $_SERVER['DOCUMENT_ROOT'] . '/tokens/token.json';
if (file_exists($tokenFile)) {
$accessToken = json_decode(file_get_contents($tokenFile), true);
$client->setAccessToken($accessToken);
if ($client->isAccessTokenExpired()) {
$client->fetchAccessTokenWithRefreshToken($client->getRefreshToken());
file_put_contents($tokenFile, json_encode($client->getAccessToken()));
}
} else {
if (!isset($_GET['code'])) {
$authUrl = $client->createAuthUrl();
echo "<a href='$authUrl'>구글 드라이브 인증</a>";
exit;
} else {
$client->authenticate($_GET['code']);
$accessToken = $client->getAccessToken();
if (!file_exists(dirname($tokenFile))) {
mkdir(dirname($tokenFile), 0700, true);
}
file_put_contents($tokenFile, json_encode($accessToken));
header('Location: ' . filter_var($client->getRedirectUri(), FILTER_SANITIZE_URL));
exit;
}
}
// Google Drive 서비스 초기화
$service = new Google_Service_Drive($client);
try {
// '미래기업' 폴더 ID 가져오기 또는 생성
$folderName = '미래기업';
$folderId = null;
// '미래기업' 폴더 검색
$response = $service->files->listFiles([
'q' => "name='$folderName' and mimeType='application/vnd.google-apps.folder' and trashed=false",
'spaces' => 'drive',
'fields' => 'files(id, name)',
]);
if (count($response->files) > 0) {
$folderId = $response->files[0]->id;
} else {
// 폴더가 없으면 생성
$folderMetadata = new Google_Service_Drive_DriveFile([
'name' => $folderName,
'mimeType' => 'application/vnd.google-apps.folder'
]);
$folder = $service->files->create($folderMetadata, ['fields' => 'id']);
$folderId = $folder->id;
echo "폴더 '미래기업'이 생성되었습니다. 폴더 ID: " . $folderId . "<br>";
}
// /imgwork 폴더에서 모든 파일을 Google Drive로 업로드
$imgworkPath = $_SERVER['DOCUMENT_ROOT'] . '/imgwork';
$files = scandir($imgworkPath);
echo "<h2>Google Drive에 파일 업로드:</h2>";
foreach ($files as $file) {
if ($file === '.' || $file === '..') continue; // 현재 및 상위 디렉토리 무시
$filePath = "$imgworkPath/$file";
$mimeType = mime_content_type($filePath);
// Google Drive 파일 메타데이터 설정
$fileMetadata = new Google_Service_Drive_DriveFile([
'name' => $file,
'parents' => [$folderId]
]);
$content = file_get_contents($filePath);
// Google Drive에 파일 업로드
try {
$uploadedFile = $service->files->create($fileMetadata, [
'data' => $content,
'mimeType' => $mimeType,
'uploadType' => 'multipart',
'fields' => 'id, webViewLink'
]);
// 모든 사용자가 볼 수 있도록 파일 권한 설정
$permission = new Google_Service_Drive_Permission([
'type' => 'anyone',
'role' => 'reader'
]);
$service->permissions->create($uploadedFile->id, $permission);
echo "파일 '{$file}'이 업로드되었습니다. 링크: <a href='" . $uploadedFile->webViewLink . "' target='_blank'>보기</a><br>";
} catch (Exception $e) {
echo "파일 '{$file}' 업로드 중 오류 발생: " . $e->getMessage() . "<br>";
}
}
// '미래기업' 폴더 내의 파일 목록 가져오기
$files = $service->files->listFiles([
'q' => "'$folderId' in parents and trashed=false",
'spaces' => 'drive',
'fields' => 'files(id, name, mimeType, createdTime, webViewLink)',
]);
echo "<h2>'미래기업' 폴더 내의 파일 목록:</h2>";
echo "<ul>";
if (count($files->files) > 0) {
foreach ($files->files as $file) {
$fileType = $file->mimeType === 'application/vnd.google-apps.folder' ? '폴더' : '파일';
echo "<li>";
echo "$fileType: <a href='" . $file->webViewLink . "' target='_blank'>" . $file->name . "</a><br>";
echo "파일 ID: " . $file->id . "<br>";
echo "생성 시간: " . $file->createdTime . "<br><br>";
echo "</li>";
}
} else {
echo "<li>폴더에 파일이 없습니다.</li>";
}
echo "</ul>";
} catch (Exception $e) {
echo '오류 발생: ' . $e->getMessage();
}
?>
코드 설명
폴더 확인 및 생성:
미래기업 폴더가 존재하지 않으면 Google Drive에 해당 폴더를 생성하고, 이미 존재하면 해당 폴더 ID를 가져옵니다.
로컬 /imgwork 폴더 파일 업로드:
/imgwork 폴더의 파일들을 순회하면서 Google Drive의 미래기업 폴더에 업로드합니다.
업로드 후 각 파일의 웹 보기 링크를 출력하여 사용자가 Google Drive에서 파일을 직접 확인할 수 있게 합니다.
파일 권한 설정:
업로드된 각 파일에 대해 "anyone with the link" 읽기 권한을 설정하여 링크로 누구나 접근할 수 있도록 합니다.
Google Drive 파일 목록 출력:
미래기업 폴더에 있는 파일 목록을 가져와 웹 페이지에 출력합니다.
각 파일은 Google Drive 링크와 함께 표시되며, 파일 생성 시간과 파일 ID도 출력됩니다.
이 코드를 사용하면 로컬의 /imgwork 폴더에 있는 모든 파일을 Google Drive에 업로드하고, 업로드된 파일 목록을 웹 페이지에서 확인할 수 있습니다.
나의 말:
<?php
require_once $_SERVER['DOCUMENT_ROOT'] . '/vendor/autoload.php';
session_start();
// Google OAuth2 클라이언트 설정
$client = new Google_Client();
$client->setClientId('201614692575-nbik0u921jg5826f4e9j22pd6mfbmuhr.apps.googleusercontent.com');
$client->setClientSecret('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');
$client->setRedirectUri('https://8440.co.kr/drive/upload.php'); // 리디렉션 URI
$client->addScope(Google_Service_Drive::DRIVE);
// 토큰 파일 경로 설정
$tokenFile = $_SERVER['DOCUMENT_ROOT'] . '/tokens/token.json';
if (file_exists($tokenFile)) {
$accessToken = json_decode(file_get_contents($tokenFile), true);
$client->setAccessToken($accessToken);
if ($client->isAccessTokenExpired()) {
$client->fetchAccessTokenWithRefreshToken($client->getRefreshToken());
file_put_contents($tokenFile, json_encode($client->getAccessToken()));
}
} else {
if (!isset($_GET['code'])) {
$authUrl = $client->createAuthUrl();
echo "<a href='$authUrl'>구글 드라이브 인증</a>";
exit;
} else {
$client->authenticate($_GET['code']);
$accessToken = $client->getAccessToken();
if (!file_exists(dirname($tokenFile))) {
mkdir(dirname($tokenFile), 0700, true);
}
file_put_contents($tokenFile, json_encode($accessToken));
header('Location: ' . filter_var($client->getRedirectUri(), FILTER_SANITIZE_URL));
exit;
}
}
// Google Drive 서비스 초기화
$service = new Google_Service_Drive($client);
try {
// '미래기업' 폴더 ID 가져오기 또는 생성
$folderName = '미래기업';
$folderId = null;
// '미래기업' 폴더 검색
$response = $service->files->listFiles([
'q' => "name='$folderName' and mimeType='application/vnd.google-apps.folder' and trashed=false",
'spaces' => 'drive',
'fields' => 'files(id, name)',
]);
if (count($response->files) > 0) {
$folderId = $response->files[0]->id;
} else {
// 폴더가 없으면 생성
$folderMetadata = new Google_Service_Drive_DriveFile([
'name' => $folderName,
'mimeType' => 'application/vnd.google-apps.folder'
]);
$folder = $service->files->create($folderMetadata, ['fields' => 'id']);
$folderId = $folder->id;
echo "폴더 '미래기업'이 생성되었습니다. 폴더 ID: " . $folderId . "<br>";
}
// /imgwork 폴더에서 모든 파일을 Google Drive로 업로드
$imgworkPath = $_SERVER['DOCUMENT_ROOT'] . '/imgwork';
$files = scandir($imgworkPath);
echo "<h2>Google Drive에 파일 업로드:</h2>";
foreach ($files as $file) {
if ($file === '.' || $file === '..') continue; // 현재 및 상위 디렉토리 무시
$filePath = "$imgworkPath/$file";
$mimeType = mime_content_type($filePath);
// Google Drive 파일 메타데이터 설정
$fileMetadata = new Google_Service_Drive_DriveFile([
'name' => $file,
'parents' => [$folderId]
]);
$content = file_get_contents($filePath);
// Google Drive에 파일 업로드
try {
$uploadedFile = $service->files->create($fileMetadata, [
'data' => $content,
'mimeType' => $mimeType,
'uploadType' => 'multipart',
'fields' => 'id, webViewLink'
]);
// 모든 사용자가 볼 수 있도록 파일 권한 설정
$permission = new Google_Service_Drive_Permission([
'type' => 'anyone',
'role' => 'reader'
]);
$service->permissions->create($uploadedFile->id, $permission);
echo "파일 '{$file}'이 업로드되었습니다. 링크: <a href='" . $uploadedFile->webViewLink . "' target='_blank'>보기</a><br>";
} catch (Exception $e) {
echo "파일 '{$file}' 업로드 중 오류 발생: " . $e->getMessage() . "<br>";
}
}
// '미래기업' 폴더 내의 파일 목록 가져오기
$files = $service->files->listFiles([
'q' => "'$folderId' in parents and trashed=false",
'spaces' => 'drive',
'fields' => 'files(id, name, mimeType, createdTime, webViewLink)',
]);
echo "<h2>'미래기업' 폴더 내의 파일 목록:</h2>";
echo "<ul>";
if (count($files->files) > 0) {
foreach ($files->files as $file) {
$fileType = $file->mimeType === 'application/vnd.google-apps.folder' ? '폴더' : '파일';
echo "<li>";
echo "$fileType: <a href='" . $file->webViewLink . "' target='_blank'>" . $file->name . "</a><br>";
echo "파일 ID: " . $file->id . "<br>";
echo "생성 시간: " . $file->createdTime . "<br><br>";
echo "</li>";
}
} else {
echo "<li>폴더에 파일이 없습니다.</li>";
}
echo "</ul>";
} catch (Exception $e) {
echo '오류 발생: ' . $e->getMessage();
}
?>
위의 코드에서 항상 새로운 파일을 만들면,
$client->setRedirectUri('https://8440.co.kr/drive/upload.php'); // 리디렉션 URI
이 코드에 맞게 OAuth2.0에 URI 추가를 해줘야 하나?
ChatGPT의 말:
ChatGPT
네, Google OAuth 2.0 인증 과정에서 setRedirectUri에 설정된 URI는 Google Cloud Console의 OAuth 2.0 클라이언트 설정에서 미리 등록되어 있어야 합니다. 매번 새로운 파일로 인증 처리를 할 경우 그 파일의 경로를 Google Cloud Console의 리디렉션 URI에 추가해 주어야 인증이 정상적으로 이루어집니다.
해결 방법
Google Cloud Console에 여러 리디렉션 URI 추가하기:
Google Cloud Console의 OAuth 클라이언트 설정에서 여러 URI를 추가할 수 있습니다.
매번 다른 경로로 인증을 테스트하거나 사용할 예정이라면, 예상되는 모든 경로를 리디렉션 URI 리스트에 미리 추가해 주세요.
예를 들어, /drive/upload.php, /drive/view.php, /drive/another.php 등이 있다면 각각을 개별 리디렉션 URI로 추가할 수 있습니다.
고정된 리디렉션 URI 사용하기:
매번 다른 파일로 인증 처리를 진행할 필요가 없다면, 하나의 고정된 파일을 리디렉션 URI로 지정하는 것도 방법입니다.
예를 들어, 모든 인증 요청을 /drive/auth.php와 같은 하나의 고정된 파일로 처리한 뒤, 인증이 완료되면 필요에 따라 다른 페이지로 리다이렉트하도록 설정할 수 있습니다.
예시: 고정된 리디렉션 URI 사용
고정 리디렉션 URI 파일 생성:
예를 들어 /drive/auth.php라는 파일을 사용하여 인증을 처리합니다.
인증 후 리다이렉트 추가:
인증이 완료된 후, 원하는 파일로 다시 이동하도록 코드에 리다이렉트를 추가합니다.
$client->setRedirectUri('https://8440.co.kr/drive/auth.php'); // 고정된 리디렉션 URI
// 인증 후 필요한 위치로 리다이렉트
if (isset($_GET['code'])) {
$client->authenticate($_GET['code']);
$_SESSION['access_token'] = $client->getAccessToken();
header('Location: https://8440.co.kr/drive/upload.php'); // 인증 후 이동할 페이지
exit;
}
이렇게 하면 Google Cloud Console에 고정된 URI만 등록해 두고, 코드 내부에서 인증 후 이동할 파일을 변경할 수 있습니다.
나의 말:
<?php
require_once $_SERVER['DOCUMENT_ROOT'] . '/vendor/autoload.php';
session_start();
// Google OAuth2 클라이언트 설정
$client = new Google_Client();
$client->setClientId('201614692575-nbik0u921jg5826f4e9j22pd6mfbmuhr.apps.googleusercontent.com');
$client->setClientSecret('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');
$client->setRedirectUri('https://8440.co.kr/drive/auth.php'); // 고정된 리디렉션 URI
// 인증 후 필요한 위치로 리다이렉트
if (isset($_GET['code'])) {
$client->authenticate($_GET['code']);
$_SESSION['access_token'] = $client->getAccessToken();
header('Location: https://8440.co.kr/drive/upload.php'); // 인증 후 이동할 페이지
exit;
}
$client->addScope(Google_Service_Drive::DRIVE);
// 토큰 파일 경로 설정
$tokenFile = $_SERVER['DOCUMENT_ROOT'] . '/tokens/token.json';
if (file_exists($tokenFile)) {
$accessToken = json_decode(file_get_contents($tokenFile), true);
$client->setAccessToken($accessToken);
if ($client->isAccessTokenExpired()) {
$client->fetchAccessTokenWithRefreshToken($client->getRefreshToken());
file_put_contents($tokenFile, json_encode($client->getAccessToken()));
}
} else {
if (!isset($_GET['code'])) {
$authUrl = $client->createAuthUrl();
echo "<a href='$authUrl'>구글 드라이브 인증</a>";
exit;
} else {
$client->authenticate($_GET['code']);
$accessToken = $client->getAccessToken();
if (!file_exists(dirname($tokenFile))) {
mkdir(dirname($tokenFile), 0700, true);
}
file_put_contents($tokenFile, json_encode($accessToken));
header('Location: ' . filter_var($client->getRedirectUri(), FILTER_SANITIZE_URL));
exit;
}
}
// Google Drive 서비스 초기화
$service = new Google_Service_Drive($client);
try {
// '미래기업' 폴더 ID 가져오기 또는 생성
$folderName = '미래기업';
$folderId = null;
// '미래기업' 폴더 검색
$response = $service->files->listFiles([
'q' => "name='$folderName' and mimeType='application/vnd.google-apps.folder' and trashed=false",
'spaces' => 'drive',
'fields' => 'files(id, name)',
]);
if (count($response->files) > 0) {
$folderId = $response->files[0]->id;
} else {
// 폴더가 없으면 생성
$folderMetadata = new Google_Service_Drive_DriveFile([
'name' => $folderName,
'mimeType' => 'application/vnd.google-apps.folder'
]);
$folder = $service->files->create($folderMetadata, ['fields' => 'id']);
$folderId = $folder->id;
echo "폴더 '미래기업'이 생성되었습니다. 폴더 ID: " . $folderId . "<br>";
}
// /imgwork 폴더에서 모든 파일을 Google Drive로 업로드
$imgworkPath = $_SERVER['DOCUMENT_ROOT'] . '/imgwork';
$files = scandir($imgworkPath);
echo "<h2>Google Drive에 파일 업로드:</h2>";
foreach ($files as $file) {
if ($file === '.' || $file === '..') continue; // 현재 및 상위 디렉토리 무시
$filePath = "$imgworkPath/$file";
$mimeType = mime_content_type($filePath);
// Google Drive 파일 메타데이터 설정
$fileMetadata = new Google_Service_Drive_DriveFile([
'name' => $file,
'parents' => [$folderId]
]);
$content = file_get_contents($filePath);
// Google Drive에 파일 업로드
try {
$uploadedFile = $service->files->create($fileMetadata, [
'data' => $content,
'mimeType' => $mimeType,
'uploadType' => 'multipart',
'fields' => 'id, webViewLink'
]);
// 모든 사용자가 볼 수 있도록 파일 권한 설정
$permission = new Google_Service_Drive_Permission([
'type' => 'anyone',
'role' => 'reader'
]);
$service->permissions->create($uploadedFile->id, $permission);
echo "파일 '{$file}'이 업로드되었습니다. 링크: <a href='" . $uploadedFile->webViewLink . "' target='_blank'>보기</a><br>";
} catch (Exception $e) {
echo "파일 '{$file}' 업로드 중 오류 발생: " . $e->getMessage() . "<br>";
}
}
// '미래기업' 폴더 내의 파일 목록 가져오기
$files = $service->files->listFiles([
'q' => "'$folderId' in parents and trashed=false",
'spaces' => 'drive',
'fields' => 'files(id, name, mimeType, createdTime, webViewLink)',
]);
echo "<h2>'미래기업' 폴더 내의 파일 목록:</h2>";
echo "<ul>";
if (count($files->files) > 0) {
foreach ($files->files as $file) {
$fileType = $file->mimeType === 'application/vnd.google-apps.folder' ? '폴더' : '파일';
echo "<li>";
echo "$fileType: <a href='" . $file->webViewLink . "' target='_blank'>" . $file->name . "</a><br>";
echo "파일 ID: " . $file->id . "<br>";
echo "생성 시간: " . $file->createdTime . "<br><br>";
echo "</li>";
}
} else {
echo "<li>폴더에 파일이 없습니다.</li>";
}
echo "</ul>";
} catch (Exception $e) {
echo '오류 발생: ' . $e->getMessage();
}
?>
위의 코드에서 구글드라이브 '미래기업' imgwork라는 폴더를 생성해서 저장하는 과정을 추가해줘.
ChatGPT의 말:
ChatGPT
아래 코드는 Google Drive에서 '미래기업' 폴더 안에 'imgwork'라는 하위 폴더를 생성하고, 로컬의 /imgwork 폴더의 파일을 해당 폴더에 업로드하는 과정을 추가한 것입니다.
수정된 코드
<?php
require_once $_SERVER['DOCUMENT_ROOT'] . '/vendor/autoload.php';
session_start();
// Google OAuth2 클라이언트 설정
$client = new Google_Client();
$client->setClientId('201614692575-nbik0u921jg5826f4e9j22pd6mfbmuhr.apps.googleusercontent.com');
$client->setClientSecret('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');
$client->setRedirectUri('https://8440.co.kr/drive/auth.php'); // 고정된 리디렉션 URI
// 인증 후 필요한 위치로 리다이렉트
if (isset($_GET['code'])) {
$client->authenticate($_GET['code']);
$_SESSION['access_token'] = $client->getAccessToken();
header('Location: https://8440.co.kr/drive/upload.php'); // 인증 후 이동할 페이지
exit;
}
$client->addScope(Google_Service_Drive::DRIVE);
// 토큰 파일 경로 설정
$tokenFile = $_SERVER['DOCUMENT_ROOT'] . '/tokens/token.json';
if (file_exists($tokenFile)) {
$accessToken = json_decode(file_get_contents($tokenFile), true);
$client->setAccessToken($accessToken);
if ($client->isAccessTokenExpired()) {
$client->fetchAccessTokenWithRefreshToken($client->getRefreshToken());
file_put_contents($tokenFile, json_encode($client->getAccessToken()));
}
} else {
if (!isset($_GET['code'])) {
$authUrl = $client->createAuthUrl();
echo "<a href='$authUrl'>구글 드라이브 인증</a>";
exit;
} else {
$client->authenticate($_GET['code']);
$accessToken = $client->getAccessToken();
if (!file_exists(dirname($tokenFile))) {
mkdir(dirname($tokenFile), 0700, true);
}
file_put_contents($tokenFile, json_encode($accessToken));
header('Location: ' . filter_var($client->getRedirectUri(), FILTER_SANITIZE_URL));
exit;
}
}
// Google Drive 서비스 초기화
$service = new Google_Service_Drive($client);
try {
// '미래기업' 폴더 ID 가져오기 또는 생성
$folderName = '미래기업';
$folderId = null;
// '미래기업' 폴더 검색
$response = $service->files->listFiles([
'q' => "name='$folderName' and mimeType='application/vnd.google-apps.folder' and trashed=false",
'spaces' => 'drive',
'fields' => 'files(id, name)',
]);
if (count($response->files) > 0) {
$folderId = $response->files[0]->id;
} else {
// 폴더가 없으면 생성
$folderMetadata = new Google_Service_Drive_DriveFile([
'name' => $folderName,
'mimeType' => 'application/vnd.google-apps.folder'
]);
$folder = $service->files->create($folderMetadata, ['fields' => 'id']);
$folderId = $folder->id;
echo "폴더 '미래기업'이 생성되었습니다. 폴더 ID: " . $folderId . "<br>";
}
// '미래기업' 폴더 내 'imgwork' 하위 폴더 생성
$imgworkFolderName = 'imgwork';
$imgworkFolderId = null;
// 'imgwork' 폴더가 이미 있는지 확인
$response = $service->files->listFiles([
'q' => "name='$imgworkFolderName' and mimeType='application/vnd.google-apps.folder' and '$folderId' in parents and trashed=false",
'spaces' => 'drive',
'fields' => 'files(id, name)',
]);
if (count($response->files) > 0) {
$imgworkFolderId = $response->files[0]->id;
} else {
// 'imgwork' 하위 폴더가 없으면 생성
$imgworkFolderMetadata = new Google_Service_Drive_DriveFile([
'name' => $imgworkFolderName,
'mimeType' => 'application/vnd.google-apps.folder',
'parents' => [$folderId]
]);
$imgworkFolder = $service->files->create($imgworkFolderMetadata, ['fields' => 'id']);
$imgworkFolderId = $imgworkFolder->id;
echo "하위 폴더 'imgwork'이 생성되었습니다. 폴더 ID: " . $imgworkFolderId . "<br>";
}
// /imgwork 폴더에서 모든 파일을 Google Drive의 '미래기업/imgwork'로 업로드
$imgworkPath = $_SERVER['DOCUMENT_ROOT'] . '/imgwork';
$files = scandir($imgworkPath);
echo "<h2>Google Drive에 파일 업로드:</h2>";
foreach ($files as $file) {
if ($file === '.' || $file === '..') continue; // 현재 및 상위 디렉토리 무시
$filePath = "$imgworkPath/$file";
$mimeType = mime_content_type($filePath);
// Google Drive 파일 메타데이터 설정
$fileMetadata = new Google_Service_Drive_DriveFile([
'name' => $file,
'parents' => [$imgworkFolderId]
]);
$content = file_get_contents($filePath);
// Google Drive에 파일 업로드
try {
$uploadedFile = $service->files->create($fileMetadata, [
'data' => $content,
'mimeType' => $mimeType,
'uploadType' => 'multipart',
'fields' => 'id, webViewLink'
]);
// 모든 사용자가 볼 수 있도록 파일 권한 설정
$permission = new Google_Service_Drive_Permission([
'type' => 'anyone',
'role' => 'reader'
]);
$service->permissions->create($uploadedFile->id, $permission);
echo "파일 '{$file}'이 업로드되었습니다. 링크: <a href='" . $uploadedFile->webViewLink . "' target='_blank'>보기</a><br>";
} catch (Exception $e) {
echo "파일 '{$file}' 업로드 중 오류 발생: " . $e->getMessage() . "<br>";
}
}
// '미래기업/imgwork' 폴더 내의 파일 목록 가져오기
$files = $service->files->listFiles([
'q' => "'$imgworkFolderId' in parents and trashed=false",
'spaces' => 'drive',
'fields' => 'files(id, name, mimeType, createdTime, webViewLink)',
]);
echo "<h2>'미래기업/imgwork' 폴더 내의 파일 목록:</h2>";
echo "<ul>";
if (count($files->files) > 0) {
foreach ($files->files as $file) {
$fileType = $file->mimeType === 'application/vnd.google-apps.folder' ? '폴더' : '파일';
echo "<li>";
echo "$fileType: <a href='" . $file->webViewLink . "' target='_blank'>" . $file->name . "</a><br>";
echo "파일 ID: " . $file->id . "<br>";
echo "생성 시간: " . $file->createdTime . "<br><br>";
echo "</li>";
}
} else {
echo "<li>폴더에 파일이 없습니다.</li>";
}
echo "</ul>";
} catch (Exception $e) {
echo '오류 발생: ' . $e->getMessage();
}
?>
수정된 내용 요약
'미래기업' 폴더 내 'imgwork' 폴더 생성:
'미래기업' 폴더가 존재하는지 확인하고, 없으면 생성합니다.
'미래기업' 폴더 안에 'imgwork' 폴더가 존재하는지 확인하고, 없으면 생성합니다.
파일 업로드 경로 변경:
/imgwork 폴더의 파일을 Google Drive의 '미래기업/imgwork' 폴더에 업로드합니다.
업로드된 파일은 모든 사용자가 접근할 수 있도록 링크를 생성합니다.
'미래기업/imgwork' 폴더 내 파일 목록 출력:
미래기업/imgwork 폴더 내에 업로드된 파일 목록을 표시하여 웹 페이지에서 링크로 파일을 참조할 수 있도록 했습니다.
이렇게 하면, /imgwork 폴더의 모든 파일이 Google Drive의 '미래기업/imgwork' 폴더에 업로드되며, 파일에 대한 액세스 링크도 생성됩니다.