15

I have some csv files uploaded as assets and now I need to fopen() them from my plugin.

I have an AssetFileModel but I have not been able to work out how to construct a full path to the file.

I can access the filename like: $asset->filename which gives me my_csv_file.csv but this is not enough for fopen() to find it.

How can I get the absolute path to the asset file?

Or at least a path that I can use with fopen() to find the file?

4 Answers 4

15

You can get the rest of the path from your asset's source and folder, I think something like this should do it:

$source = $asset->getSource();

if ($source->type != 'Local')
{
    throw new Exception(Craft::t('Paths not available for non-local asset sources'));
}

$sourcePath = $source->settings['path'];
$folderPath = $asset->getFolder()->path;

$assetFilePath = $sourcePath.$folderPath.$asset->filename;
3
  • Doesn't work for me :( it results in {basePath}uploads/example.png which isn't a valid path obviously
    – Stalinko
    Commented Mar 15, 2018 at 11:37
  • @Stalinko You can use craft()->config->parseEnvironmentString() to replace {basePath} with the config basePath like this $assetFilePath = craft()->config->parseEnvironmentString($sourcePath.$folderPath.$asset->filename); Commented Oct 14, 2020 at 14:35
  • thanks @K.Rijpstra but I haven't been working with craft cms since 2018 :))
    – Stalinko
    Commented Oct 15, 2020 at 3:01
12

Update for Craft 3:

To get the same output as Mike's path above, you can use:

$volumePath = $asset->getVolume()->settings['path'];
$folderPath = $asset->getFolder()->path;
$assetFilePath = Yii::getAlias($volumePath) . $folderPath . $asset->filename;
1
  • 1
    This may only work for assets at the top-level of an asset volume. Apt to need an intermediate $folderPath = $asset->getFolder()->path;, like the Craft 2 answer. Commented Jun 20, 2018 at 15:34
5

Here is an approach in Craft 4. This approach assumes you have an asset element (craft\elements\Asset).

use Craft;
//$asset = craft\elements\Asset;
$fsPath = Craft::getAlias($asset->getVolume()->fs->path);
$attachment = $fsPath . DIRECTORY_SEPARATOR . $asset->getPath();
4

See Asset::getImageTransformSourcePath() for how Craft CMS resolves the real local path. (https://github.com/craftcms/cms/blob/develop/src/elements/Asset.php#L1200)

Should look something like this:

$volume = $this->getVolume();
$assetFilePath = $volume instanceof LocalVolumeInterface
  ? FileHelper::normalizePath($volume->getRootPath() . DIRECTORY_SEPARATOR . $this->getPath())
  : null;

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.