Azure / azure-storage-android

Microsoft Azure Storage Library for Android
Apache License 2.0
81 stars 47 forks source link

Not able to upload image to blob storage - exception com.microsoft.azure.storage.StorageException: The specified resource does not exist. in line -> blobFromSASCredential.uploadFromFile(mPhotoFileUri.getPath()); #17

Closed amanpwl92 closed 8 years ago

amanpwl92 commented 9 years ago

Here's my code in onCreate method :

protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_to_do);
    btnPreview = (Button) findViewById(R.id.buttonPreview);
    btnUpload = (Button) findViewById(R.id.buttonUpload);

    btnPreview.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {
            takePicture(v);
        }
    });

    btnUpload.setOnClickListener(new View.OnClickListener() {

        @Override
        public void onClick(View v) {
            uploadPhoto(v);

        }
    });

}

Other methods called from onCreate(directly or indirectly) -

// Create a File object for storing the photo private File createImageFile() throws IOException { // Create an image file name String timeStamp = new SimpleDateFormat("yyyyMMddHHmmss").format(new Date()); String imageFileName = "JPEG" + timeStamp + "_"; File storageDir = Environment.getExternalStoragePublicDirectory(Environment.DIRECTORYPICTURES); File image = File.createTempFile( imageFileName, /* prefix / ".jpg", / suffix / storageDir /_ directory */ ); return image; }

public void takePicture(View view) {
    Intent takePictureIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
    // Ensure that there's a camera activity to handle the intent
    if (takePictureIntent.resolveActivity(getPackageManager()) != null) {
        // Create the File where the photo should go
        try {
            mPhotoFile = createImageFile();
        } catch (IOException ex) {
            // Error occurred while creating the File
            //
        }
        // Continue only if the File was successfully created
        if (mPhotoFile != null) {
            mPhotoFileUri = Uri.fromFile(mPhotoFile);
            takePictureIntent.putExtra(MediaStore.EXTRA_OUTPUT, mPhotoFileUri);
            startActivityForResult(takePictureIntent, REQUEST_TAKE_PHOTO);
        }
    }
}

public void uploadPhoto(View view) {
    MobileServiceClient mClient = null;
    try {
        mClient = new MobileServiceClient(
                "https://twokilo.azure-mobile.net/", // Replace with the above Site URL
                "bprbEdBfMdPozKNKnLcUQKPEgUKgof22",           // replace with the Application Key
                this);
    } catch (Exception e) {
    }
    if (mClient == null) {
        return;
    }
    final MobileServiceTable<Prescription> prescriptionTable = mClient.getTable("medic_orders_prescriptions", Prescription.class);
    // Create a new item
    final Prescription prescription = new Prescription();

    prescription.setUser("test");
    prescription.setMedic_order("test");
    prescription.setFull_flag(true);
    prescription.setNote("Test Note");
    prescription.setContainerName("prescriptions");

    // Use a unigue GUID to avoid collisions.
    UUID uuid = UUID.randomUUID();
    String uuidInString = uuid.toString();
    prescription.setResourceName(uuidInString);

    // Send the item to be inserted. When blob properties are set this
    // generates an SAS in the response.
    AsyncTask<Void, Void, Void> task = new AsyncTask<Void, Void, Void>() {
        @Override
        protected Void doInBackground(Void... params) {
            try {
                android.os.Debug.waitForDebugger();
                final Prescription entity = prescriptionTable.insert(prescription).get();
                ;

                // If we have a returned SAS, then upload the blob.
                if (entity.getSasQueryString() != null) {

                    // Get the URI generated that contains the SAS
                    // and extract the storage credentials.
                    StorageCredentials cred =
                            new StorageCredentialsSharedAccessSignature(entity.getSasQueryString());
                    URI imageUri = new URI(entity.getPrescription());

                    // Upload the new image as a BLOB from a stream.
                    CloudBlockBlob blobFromSASCredential =
                            new CloudBlockBlob(imageUri, cred);
                    String fileName = mPhotoFileUri.toString();
                    blobFromSASCredential.uploadFromFile(mPhotoFileUri.getPath());
                }
            } catch (final Exception e) {
                Log.i("exception", "fat gyi");
            }
            return null;
        }
    };

    task.execute();

}

}

emgerner-msft commented 9 years ago

entity.getSasQueryString()

How are you generating the sas query string?

amanpwl92 commented 9 years ago

var azure = require('azure'); var qs = require('querystring'); var appSettings = require('mobileservice-config').appSettings;

function insert(item, user, request) {

var accountName = appSettings.STORAGE_ACCOUNT_NAME;
var accountKey = appSettings.STORAGE_ACCOUNT_ACCESS_KEY;
var host = accountName + '.blob.core.windows.net';

var blobService = azure.createBlobService(accountName, accountKey, host);

// Provide write access to the container for the next 5 mins.        
var sharedAccessPolicy = {
    AccessPolicy: {
        Permissions: azure.Constants.BlobConstants.SharedAccessPermissions.WRITE,
        Expiry: new Date(new Date().getTime() + 5 * 60 * 1000)
    }
};

// Generate the upload URL with SAS for the new image.
var sasQueryUrl =
    blobService.generateSharedAccessSignature('prescriptions',
        item.resourcename, sharedAccessPolicy);

// Set the full path on the new new item, 
// which is used for data binding on the client. 
item.imageUri = sasQueryUrl.baseUrl + sasQueryUrl.path;
request.execute();

}

emgerner-msft commented 9 years ago

I'm still unclear what getSasQueryString returns and I see a couple issues with the Node code you've published:

  1. What version of the storage Node lib is this on? At least in the newer versions generateSharedAccessSignature returns just the SAS query, not an entire URL.
  2. Assuming you have a valid url, I see you've taken only the baseURL and the path, but SAS is a query. Where are you actually doing anything with the SAS token?
lanrehnics commented 8 years ago

Am having this kind of exception too but when I get the exception message ..It goes like "Address is a relative address. Only absolute address are permitted" So the question is how do I generate Absolute address..

emgerner-msft commented 8 years ago

That exception message means something pretty different I think. Could you post a new issue with the segment of your code having an issue and a stack trace please?

lanrehnics commented 8 years ago

Have Opened it.. Thanks looking forward to your reply..

emgerner-msft commented 8 years ago

@amanpwl92 Haven't heard anything since Sep so closing this issue. Feel free to reopen with any follow up or start up a new issue if you have additional questions!