問題描述
使用阿里云對象存儲OSS過程中,對于不再需要的Bucket,在使用OSS SDK、ossutil等工具刪除或者在控制臺刪除時,刪除失敗,相應的報錯信息如下:
使用OSS SDK或者ossutil工具刪除Bucket時,提示“The bucket you tried to delete is not empty”錯誤。
在OSS管理控制臺中刪除Bucket時,提示“Bucket不為空,請檢查該Bucket是否包含未刪除的Object或者未成功的Multipart碎片”錯誤。
問題原因
需要刪除的Bucket中有未刪除的Object、碎片、Livechannel或未完成的分片上傳任務,為了防止誤刪除的發生,OSS不允許刪除一個非空的Bucket。
解決方案
由于刪除Bucket后數據不可恢復,請您確保數據備份完成后,刪除該Bucket下的所有文件(Object)、碎片(Part)以及Livechannel,再次操作刪除Bucket,請參見以下操作刪除Bucket:
檢查Bucket中是否存在未刪除的文件和碎片
如何刪除的Bucket中不存在文件和碎片,具體操作如下:
登錄OSS管理控制臺。
在文件列表頁簽下,查看下是否存在文件。
如果存在,可以選擇一個或多個文件,選擇徹底刪除,刪除文件。或者通過工具ossuti刪除,詳情請參見使用ossutil工具刪除Bucket、文件和碎片。
如果不存在,請繼續執行下一步。
使用ossutil工具,執行以下命令,刪除Bucket。如果還是存在Bucket不為空的報錯,請繼續執行下一步。
./ossutil rm oss://[$Bucket_Name] -bar
說明[$Bucket_Name]為Bucket名稱。
檢查是否存在歷史版本Object
版本控制是針對存儲空間(Bucket)級別的數據保護功能。開啟版本控制后,針對數據的覆蓋和刪除操作將會以歷史版本的形式保存下來。在錯誤覆蓋或者刪除文件(Object)后,您可以將Bucket中存儲的Object恢復至任意時刻的歷史版本。但是通過控制臺和工具查看(不指定版本號的查詢)只顯示最新數據,歷史版本不顯示。刪除歷史版本Object的方法如下:
使用OSS管理控制臺
登錄OSS管理控制臺。
單擊Bucket 列表,然后單擊目標Bucket名稱。
在左側導航欄,選中數據安全 > 版本控制,檢查是否開啟了版本控制功能。如果開啟了版本控制功能,請執行以下操作,刪除歷史版本Object。
使用ossutil工具
通過執行以下命令查看是否開啟版本控制功能,詳情請參見bucket-versioning(版本控制)。
./ossutil bucket-versioning --method get oss://[$Bucket_Name]
系統顯示類似如下。
bucket versioning status:Enabled
如果開啟了版本控制功能,則返回結果為Enabled,可執行以下命令,刪除Bucket中的歷史版本Object數據。
./ossutil rm oss://[$Bucket_Name]/ --all-versions -r
系統顯示類似如下。
如果未開啟版本控制功能,則返回結果為Disable。
排查Bucket中是否存在LiveChannel
Bucket的LiveChannel查看和刪除暫不支持通過工具和控制臺操作,可以使用接口或者是SDK來實現操作,請參見DeleteLiveChannel,刪除指定的LiveChannel。示例代碼如下:
import java.util.List;
import com.alibaba.fastjson.JSON;
import com.aliyun.oss.ClientException;
import com.aliyun.oss.OSS;
import com.aliyun.oss.OSSClientBuilder;
import com.aliyun.oss.OSSException;
import com.aliyun.oss.model.CreateLiveChannelRequest;
import com.aliyun.oss.model.CreateLiveChannelResult;
import com.aliyun.oss.model.ListLiveChannelsRequest;
import com.aliyun.oss.model.LiveChannelGenericRequest;
import com.aliyun.oss.model.LiveChannelListing;
import com.aliyun.oss.model.LiveChannelStatus;
import com.aliyun.oss.model.LiveChannelTarget;
import com.aliyun.oss.model.LiveChannel;
import com.aliyun.oss.common.auth.*;
public class DeleteLiveChannel {
private static String endpoint = "http://oss-cn-hangzhou.aliyuncs.com";
private static final
/**
* 通過環境變量獲取訪問憑證
*/
private static final EnvironmentVariableCredentialsProvider CREDENTIALS_PROVIDER = CredentialsProviderFactory.newEnvironmentVariableCredentialsProvider();
private static String bucketName = "bucktname";
public static void createLiveChannel() {
// 創建OSSClient實例。
String liveChannelName = "liveChannelName1";
OSS oss = new OSSClientBuilder().build(endpoint, CREDENTIALS_PROVIDER);
CreateLiveChannelRequest request = new CreateLiveChannelRequest(bucketName,
liveChannelName, "desc", LiveChannelStatus.Enabled, new LiveChannelTarget());
CreateLiveChannelResult result = oss.createLiveChannel(request);
//獲取推流地址。
List<String> publishUrls = result.getPublishUrls();
for (String item : publishUrls) {
System.out.println(item);
}
//獲取播放地址。
List<String> playUrls = result.getPlayUrls();
for (String item : playUrls) {
System.out.println(item);
}
oss.shutdown();
}
public static void listLiveChannels() {
// 創建OSSClient實例。
OSS oss = new OSSClientBuilder().build(endpoint, CREDENTIALS_PROVIDER);
ListLiveChannelsRequest request = new ListLiveChannelsRequest(bucketName);
LiveChannelListing liveChannelListing = oss.listLiveChannels(request);
List<LiveChannel> list = liveChannelListing.getLiveChannels();
for(LiveChannel i:list){
deleteLiveChannel(i.getName());
}
oss.shutdown();
}
public static void deleteLiveChannel(String liveChannelName) {
// 創建OSSClient實例。
OSS oss = new OSSClientBuilder().build(endpoint, CREDENTIALS_PROVIDER);
LiveChannelGenericRequest request = new LiveChannelGenericRequest(bucketName, liveChannelName);
System.out.println("Delete liveChanne "+liveChannelName+" Done");
try {
oss.deleteLiveChannel(request);
} catch (OSSException ex) {
ex.printStackTrace();
} catch (ClientException ex) {
ex.printStackTrace();
} finally {
oss.shutdown();
}
}
public static void main(String[] args) {
// TODO Auto-generated method stub
DeleteLiveChannel.listLiveChannels();
}
}