// // Project Config // void SaveProjectConfig() { JSONNode configJson = Utils.GetProjectSettingsJsonNode(); if (configJson == null) { configJson = JSONNode.Parse("{}"); } configJson["PackingDirectories"] = JsonHelper.ToJsonArray(PackingDirectories.Directories); foreach (TransferMode t in Enum.GetValues(typeof(TransferMode))) { int modeInt = (int)t; string modeString = Enum.GetName(typeof(TransferMode), t); configJson["taskId"][modeString] = ContextForMode[(int)t].taskId; configJson["repoInfo"][modeString]["repoUsername"] = ContextForMode[modeInt].repoUsername; configJson["repoInfo"][modeString]["repoPassword"] = ContextForMode[modeInt].repoPassword; configJson["repoInfo"][modeString]["repoUrl"] = ContextForMode[modeInt].repoUrl; configJson["repoInfo"][modeString]["repoBranch"] = ContextForMode[modeInt].repoBranch; configJson["repoInfo"][modeString]["repoToken"] = ContextForMode[modeInt].repoToken; } Debug.Log("Save Project Config: " + configJson); Utils.SaveProjectSettings(configJson); }
void StartCloudBuildAction() { //check if IL2CPP if (ContextForMode[transferModeFlag].BadScriptingBackend()) { EditorUtility.DisplayDialog("Error", "Can't start Cloud Build.\nScripting Backend: IL2CPP detected. To some build targets [Standalone, OSX, Android], IL2CPP is not supported. Please check you player settings.", "OK"); return; } ContextForMode[transferModeFlag].HideProgress(); ContextForMode[transferModeFlag].ResetJobsWithActionsOpened(); JSONNode data = BuildStartCloudBuildOptions(); try { JSONNode response = ucbFacade.PostTask(data); ContextForMode[transferModeFlag].taskId = response["taskUuid"]; ContextForMode[transferModeFlag].taskInfo = response; ContextForMode[transferModeFlag].UpdateSyncTaskInterval(); SaveProjectConfig(); Debug.Log(string.Format(@"Build Task [{0}] started with Jobs [{1}].", ContextForMode[transferModeFlag].taskId, response["jobs"].ToString())); } catch (Exception ex) { Debug.LogError(ex); ShowNotification(new GUIContent(ex.Message)); } }
string GetLatestZip() { string[] fileNames = Directory.GetFiles(PathHelper.ZipDirectory); string result = null; DateTime latestZipTime = DateTime.MinValue; foreach (string fileName in fileNames) { if (fileName.Contains(".zip")) { DateTime thisZipTime = File.GetLastWriteTime(fileName); if (thisZipTime > latestZipTime) { result = fileName; latestZipTime = thisZipTime; } } } if (!string.IsNullOrEmpty(result)) { PathHelper.ProjectZipFullPath = result; Debug.Log(PathHelper.ProjectZipFullPath); return(File.GetLastWriteTime(result).ToLongTimeString()); } return(null); }
// // Upload // void StartUploadProject() { SaveGlobalConfig(); //check if IL2CPP if (Utils.IL2CPP()) { EditorUtility.DisplayDialog("Warning", "Scripting Backend: IL2CPP detected. Please notice, to some build targets [Standalone, OSX, Android], IL2CPP is not supported.", "OK"); } try { ContextForMode[transferModeFlag].StartUploadProject(PathHelper.ProjectZipFullPath, ftpInstance); } catch (Exception ex) { if (ex.GetType() == typeof(CosFileExistsException)) { ShowNotification(new GUIContent("File Exists")); } else { Debug.LogError(ex); ShowNotification(new GUIContent("Upload Failed")); } } }
public static void showWindow() { Debug.Log("Unity Version: " + unityVersion); if (UcbFacade.GetInstance().CheckUnityVersion(unityVersion)) { EditorWindow.GetWindow(typeof(UcbEditorWindow)); } else { EditorUtility.DisplayDialog("Unsupported Unity Version", "You are using a version of Unity Editor that is not supported by Cloud Build Plugin.", "OK"); } }
void CancelCloudBuildAction() { if (!string.IsNullOrEmpty(ContextForMode[transferModeFlag].taskId)) { try { ucbFacade.CancelTask(ContextForMode[transferModeFlag].taskId); } catch (Exception ex) { Debug.LogError(ex); ShowNotification(new GUIContent(ex.Message)); } } }
// public async Task AsyncUploadProject(string fileName, string projectId, IProgress<double> progress) // { // AsyncFunction(fileName, projectId, progress); // } // private Task AsyncFunction(string fileName, string projectId, IProgress<double> progress) // { // return Task.Run(() => // { // UploadProject(fileName, projectId, progress); // return; // }); // } public void AsyncUploadProject(string fileName, string projectId, IProgress <double> progress, OnCompleteCallback onComplete) { Func <string, string, IProgress <double>, Exception> fun = t_UploadProject; fun.BeginInvoke(fileName, projectId, progress, (ar => { Debug.Log("Async FTP Upload Ended."); if (ar == null) { throw new ArgumentNullException("ar"); } Func <string, string, IProgress <double>, Exception> dl = (Func <string, string, IProgress <double>, Exception>)ar.AsyncState; Exception result = dl.EndInvoke(ar); onComplete(result); }), fun); Debug.Log("Async FTP Upload Start."); }
void LoadGlobalConfig() { try { string configJsonString = File.ReadAllText(PathHelper.GlobalConfigPath); JSONNode configJson = JSON.Parse(configJsonString); ftpHost = configJson["ftpHost"]; ftpPort = configJson["ftpPort"]; ftpUserName = configJson["ftpUserName"]; ftpPassword = configJson["ftpPassword"]; apiHost = configJson["apiHost"]; apiPort = configJson["apiPort"]; cosEndPoint = configJson["cosEndPoint"]; } catch (Exception ex) { Debug.Info("No Global Config"); } }
// // Global config // // Save user related information to appdata path of Unity editor. // void SaveGlobalConfig() { try { JSONNode configJson = JSON.Parse("{}"); configJson["ftpHost"] = ftpHost; configJson["ftpPort"] = ftpPort; configJson["ftpUserName"] = ftpUserName; configJson["ftpPassword"] = ftpPassword; configJson["apiHost"] = apiHost; configJson["apiPort"] = apiPort; configJson["cosEndPoint"] = cosEndPoint; File.WriteAllText(PathHelper.GlobalConfigPath, configJson.ToString()); } catch (Exception ex) { Debug.LogError(ex); } }
// // Pack // void StartPackingProject() { OnZipProgressChange(0f); try { ZipHandler.CleanPreviousZip(PathHelper.ZipDirectory); PathHelper.ProjectZipFullPath = ZipHandler.CompressProject(PathHelper.ProjectDirectory, PathHelper.ZipDirectory + "project-pack.zip", new BasicProgress <double>(OnZipProgressChange)); Debug.Log(PathHelper.ProjectZipFullPath); } catch (IOException ex) { //file hash exists Debug.LogError(ex); ShowNotification(new GUIContent(ex.Message)); } finally { EditorUtility.ClearProgressBar(); } }
void LoadProjectConfig() { JSONNode configJson = Utils.GetProjectSettingsJsonNode(); if (configJson == null) { Debug.Info("Load Project Config: Nothing to lowwwwad"); return; } List <string> pDirs = JsonHelper.ToStringList(configJson["PackingDirectories"].AsArray); if (pDirs.Count > 0 && pDirs[0].Contains(PathHelper.ProjectDirectory)) { PackingDirectories.Directories = pDirs; } else { if (pDirs.Count > 0) { Debug.LogError("Failed loading Packing Directories. Please config it again before do Packing."); } PackingDirectories.InitPackingDirectories(); } foreach (TransferMode t in Enum.GetValues(typeof(TransferMode))) { int modeInt = (int)t; string modeString = Enum.GetName(typeof(TransferMode), t); ContextForMode[modeInt].taskId = configJson["taskId"][modeString]; ContextForMode[modeInt].repoUsername = configJson["repoInfo"][modeString]["repoUsername"]; ContextForMode[modeInt].repoPassword = configJson["repoInfo"][modeString]["repoPassword"]; ContextForMode[modeInt].repoUrl = configJson["repoInfo"][modeString]["repoUrl"]; ContextForMode[modeInt].repoBranch = configJson["repoInfo"][modeString]["repoBranch"]; ContextForMode[modeInt].repoToken = configJson["repoInfo"][modeString]["repoToken"]; } }
// // Life cycle // private void OnEnable() { guiDefaultColor = GUI.color; autoRepaintOnSceneChange = true; minSize = new Vector2(350, 650); try { GetLatestZip(); LoadProjectConfig(); LoadGlobalConfig(); } catch (Exception ex) { Debug.LogError(ex); } showExtraFields_Upload = new AnimBool(true); showExtraFields_Upload.valueChanged.AddListener(Repaint); SyncBuildTaskInfo(); }
bool IsBuildJobDone(int index) { if (ContextForMode[transferModeFlag].taskInfo == null || ContextForMode[transferModeFlag].taskInfo["jobs"].IsNull) { return(false); } bool result = false; try { int status = (int)Enum.Parse(typeof(JobStatus), ContextForMode[transferModeFlag].taskInfo["jobs"][index]["status"]); if (status > (int)JobStatus.RUNNING && status != (int)JobStatus.CANCELLED) { result = true; } } catch (Exception ex) { Debug.LogError(ex); } return(result); }
// // UI // void OnGUI() { scrollPos = EditorGUILayout.BeginScrollView(scrollPos, GUILayout.Width(position.width), GUILayout.Height(position.height)); EditorGUILayout.LabelField("Mode", EditorStyles.boldLabel); EditorGUI.indentLevel++; int newMode = EditorGUILayout.Popup("Cloud Build Mode:", transferModeFlag, transferModeOptions, EditorStyles.popup); if (newMode != transferModeFlag) { transferModeFlag = newMode; OnTransferModeChange(); } if (TransferMode.FTP.Equals(ContextForMode[transferModeFlag].transferMode)) { EditorGUILayout.LabelField("* for internal use only"); } EditorGUI.indentLevel--; // // Upload // if (TransferModeUtils.IsRepository(transferModeFlag)) { EditorGUILayout.Separator(); EditorGUI.indentLevel++; ContextForMode[transferModeFlag].repoUrl = EditorGUILayout.TextField("Repository URL:", ContextForMode[transferModeFlag].repoUrl); if (transferModeFlag == (int)TransferMode.GIT) { ContextForMode[transferModeFlag].repoBranch = EditorGUILayout.TextField("Branch name:", ContextForMode[transferModeFlag].repoBranch); gitCredentialModeFlag = EditorGUILayout.Popup("Credential Mode:", gitCredentialModeFlag, gitCredentialOptions, EditorStyles.popup); } ContextForMode[transferModeFlag].relativePath = EditorGUILayout.TextField(new GUIContent("Relative Path (?):", "Unity project path relative to repository root"), ContextForMode[transferModeFlag].relativePath); if (transferModeFlag == (int)TransferMode.GIT && gitCredentialModeFlag == (int)GitCredentialMode.GitToken) { ContextForMode[transferModeFlag].repoToken = EditorGUILayout.TextField("Git Token:", ContextForMode[transferModeFlag].repoToken); } else { ContextForMode[transferModeFlag].repoUsername = EditorGUILayout.TextField("Repo Username:"******"Repo Password:"******"Upload", EditorStyles.boldLabel); EditorGUI.indentLevel++; GUIStyle wraptStyle = new GUIStyle(EditorStyles.label); wraptStyle.wordWrap = true; EditorGUILayout.LabelField("* Remember to config Build-Settings for your build target(s), and SAVE project before packing.", wraptStyle); if (GUILayout.Button("Config Packing Directories")) { UcbPackDirectoriesWindow.showWindow(); } if (GUILayout.Button("Pack")) { if (UcbFacade.GetInstance().CheckUnityVersion(unityVersion)) { StartPackingProject(); } else { ShowNotification(new GUIContent("Unsupported Unity version")); } } if (!string.IsNullOrEmpty(PathHelper.ProjectZipFullPath)) { EditorGUILayout.LabelField("Latest Local Pack:", File.GetLastWriteTime(PathHelper.ProjectZipFullPath).ToString()); } if (transferModeFlag == (int)TransferMode.FTP) { ftpHost = EditorGUILayout.TextField("FTP Host:", ftpHost); ftpPort = EditorGUILayout.TextField("FTP Port:", ftpPort); ftpUserName = EditorGUILayout.TextField("FTP Username:"******"FTP Password:"******"Upload Mode:", ContextForMode[transferModeFlag].cosUploadModeFlag, cosUploadModeOptions, EditorStyles.popup); } string uploadBtnText = "Upload"; if (ContextForMode[transferModeFlag].isUploading || string.IsNullOrEmpty(PathHelper.ProjectZipFullPath)) { GUI.enabled = false; if (ContextForMode[transferModeFlag].isUploading) { uploadBtnText = "Uploading..."; } } if (GUILayout.Button(uploadBtnText)) { StartUploadProject(); } GUI.enabled = true; EditorGUI.indentLevel--; } // // Build // EditorGUILayout.Separator(); EditorGUILayout.LabelField("Build", EditorStyles.boldLabel); EditorGUI.indentLevel++; string latestBuildTime = GetLatestBuildTimeString(); EditorGUILayout.LabelField("Select Build Target(s)"); EditorGUI.indentLevel++; for (int i = 0; i < ContextForMode[transferModeFlag].buildTargetSelection.Length; i++) { string buildTargetName = Enum.GetNames(typeof(BuildTarget))[i]; Rect statusRect = EditorGUILayout.BeginHorizontal(GUILayout.Width(290)); EditorGUILayout.LabelField(buildTargetName); ContextForMode[transferModeFlag].buildTargetSelection[i] = EditorGUILayout.Toggle(ContextForMode[transferModeFlag].buildTargetSelection[i]); EditorGUILayout.EndHorizontal(); } EditorGUI.indentLevel--; if (ContextForMode[transferModeFlag].IsBuildTaskRunning()) { if (GUILayout.Button("Cancel Cloud Build")) { CancelCloudBuildAction(); } } else { if (GUILayout.Button("Start Cloud Build")) { if (!TransferModeUtils.IsRepository(transferModeFlag) && !ContextForMode[transferModeFlag].projectUploaded) { ShowNotification(new GUIContent("No Project Uploaded")); } else if (!IsBuildTargetSelected()) { ShowNotification(new GUIContent("Select Build Target")); } else { StartCloudBuildAction(); } } } if (!string.IsNullOrEmpty(latestBuildTime)) { EditorGUILayout.LabelField("Latest Build:", latestBuildTime); } if (string.IsNullOrEmpty(ContextForMode[transferModeFlag].taskId) || ContextForMode[transferModeFlag].taskInfo == null) { EditorGUILayout.LabelField("Build Status", "Not Started"); } else { EditorGUILayout.LabelField("Build Status"); EditorGUI.indentLevel++; JSONArray jobs = ContextForMode[transferModeFlag].taskInfo["jobs"].AsArray; for (int i = 0; i < jobs.Count; i++) { string statusString = jobs[i]["status"]; if (statusString == "FAILED") { GUI.color = new Color(255, 0, 0); } Rect statusRect = EditorGUILayout.BeginHorizontal(GUILayout.Width(290)); EditorGUILayout.LabelField(jobs[i]["buildTarget"], GUILayout.Width(170)); EditorGUILayout.LabelField(statusString, GUILayout.Width(100)); GUI.color = guiDefaultColor; if (IsBuildJobDone(i)) { if (GUILayout.Button("Actions", GUILayout.Width(60), GUILayout.Height(14))) { if (!ContextForMode[transferModeFlag].jobActionOpened.ContainsKey(jobs[i]["name"])) { ContextForMode[transferModeFlag].jobActionOpened[jobs[i]["name"]] = true; } else { ContextForMode[transferModeFlag].jobActionOpened[jobs[i]["name"]] = !ContextForMode[transferModeFlag].jobActionOpened[jobs[i]["name"]]; } } } EditorGUILayout.EndHorizontal(); if (ContextForMode[transferModeFlag].jobActionOpened.ContainsKey(jobs[i]["name"]) && ContextForMode[transferModeFlag].jobActionOpened[jobs[i]["name"]] == true) { //download button group try { if (jobs[i]["downloadLink"] != null) { if (GUILayout.Button("Download")) { Application.OpenURL(jobs[i]["downloadLink"]); EditorUtility.ClearProgressBar(); } if (GUILayout.Button("Copy Download URL")) { EditorGUIUtility.systemCopyBuffer = jobs[i]["downloadLink"]; ShowNotification(new GUIContent("Copied URL" + Environment.NewLine + " to clipboard")); EditorUtility.ClearProgressBar(); } if (jobs[i]["downloadLink"].ToString().Contains(".apk")) { if (GUILayout.Button("QR Code")) { UcbQrPopup.Open(jobs[i]["downloadLink"], "Cloud Build Download Apk", "Scan QR code to download apk" + Environment.NewLine + "direct into your mobile devices"); } } } // //build just finished // if (jobs[i]["exectionLog"] != null || jobs[i]["logLink"] != null) { if (GUILayout.Button("Print Log")) { ShowNotification(new GUIContent("Printed to" + Environment.NewLine + "console")); if (jobs[i]["exectionLog"] != null) { Debug.Info("Build Execution Log :" + jobs[i]["exectionLog"]); } if (jobs[i]["logLink"] != null) { Debug.Info("Editor Log in Link:" + jobs[i]["logLink"]); Debug.Info("Editor Log Content:" + ftpInstance.GetEditorLog(jobs[i]["logLink"])); } } EditorGUILayout.Separator(); } } catch (NullReferenceException ex) { } } } EditorGUI.indentLevel--; } if (ContextForMode[transferModeFlag].taskId != null) { if (GUILayout.Button("Track This Task by WeChat")) { string url = Constants.WEAPP_QR_PREFIX + ContextForMode[transferModeFlag].taskId; UcbQrPopup.Open(url, "QR for WeApp Monitor", "Scan QR code by WeChat" + Environment.NewLine + "to monitor this task"); } } EditorGUI.indentLevel--; if (ContextForMode[transferModeFlag].isProgressBarVisible) { string text = ContextForMode[transferModeFlag].progressTitle; if (1 - ContextForMode[transferModeFlag].progressValue > 0.0001) { text += String.Format(" [ {0}% ]", (int)(ContextForMode[transferModeFlag].progressValue * 100)); } EditorGUI.ProgressBar(new Rect(3, position.height - 30, position.width - 6, 20), ContextForMode[transferModeFlag].progressValue, text); } EditorGUILayout.Separator(); GUIStyle foldOutStyle = new GUIStyle(EditorStyles.foldout); foldOutStyle.fontStyle = FontStyle.Bold; showAdvancedSettings = EditorGUILayout.Foldout(showAdvancedSettings, "Advanced Settings", foldOutStyle); if (showAdvancedSettings) { EditorGUI.indentLevel++; apiHost = EditorGUILayout.TextField("API Host:", apiHost); apiPort = EditorGUILayout.TextField("API Port:", apiPort); cosEndPoint = EditorGUILayout.TextField("COS Host:", cosEndPoint); EditorGUI.indentLevel--; } EditorGUILayout.EndScrollView(); }
public void UploadProject(string fileName, string projectId, IProgress <double> progress) { long offset = GetFileOffset(fileName, projectId); Console.WriteLine("file offset {0}", offset); long fileLength = new FileInfo(fileName).Length; if (offset == fileLength) { throw new CosFileExistsException("File Exists"); } Debug.Log(string.Format(@"Start to upload zip file to ftp server - {0}", DateTime.Now)); Uri uri = new Uri(string.Format(@"ftp://{0}:{1}/{2}/{3}", remoteHost, remotePort, projectId, Path.GetFileName(fileName))); Debug.Log(string.Format(@"ftp url is {0} - {1}", uri, DateTime.Now)); FtpWebRequest request = (FtpWebRequest)WebRequest.Create(uri); request.Credentials = new NetworkCredential(username, password); request.UsePassive = false; request.KeepAlive = true; request.UseBinary = true; request.ContentOffset = offset; if (offset > 0L) { request.Method = WebRequestMethods.Ftp.AppendFile; } else { request.Method = WebRequestMethods.Ftp.UploadFile; } Debug.Log(string.Format(@"*** {0} ***", DateTime.Now)); Stream dest = request.GetRequestStream(); Debug.Log(string.Format(@"*** {0} ***", DateTime.Now)); FileStream src = File.OpenRead(fileName); src.Position = offset; int bufSize = (int)Math.Min(src.Length, 2048); byte[] buffer = new byte[bufSize]; int bytesRead = 0; long currentBytes = 0; do { bytesRead = src.Read(buffer, 0, bufSize); dest.Write(buffer, 0, bufSize); currentBytes += bytesRead; progress.Report(currentBytes / (double)src.Length); }while (bytesRead != 0); dest.Close(); src.Close(); Debug.Log(string.Format(@"Finish to upload zip file to ftp server - {0}", DateTime.Now)); using (FtpWebResponse response = (FtpWebResponse)request.GetResponse()) { Debug.Log("Upload File Complete, status " + response.StatusDescription); } }