Accessing container fields with PHP


Warning: copy(): Filename cannot be empty in C:\inetpub\blog.myfmbutler.com\wp-content\plugins\mytube\mytube.php on line 220

In this tutorial, we are going to look at how you can access the contents of a container field in FileMaker using the FileMaker PHP API. We will make a web page that lists all the records in our database and which allows us to download the data from the container field using a link.

For this example, we're assuming you've already setup your database for PHP web access. If you haven't done this, please refer to the FileMaker documentation on how to do this.

1. Creating the index page

The first step is to create an index.php page which lists all the records in the database as links:

  1. <?php
  2.  
  3. // Include the FileMaker API
  4. require_once('FileMaker.php');
  5.  
  6. // Make a connection with the FileMaker server
  7. $fm = & new FileMaker();
  8. $fm->setProperty('hostspec', 'http://localhost');
  9. $fm->setProperty('database', 'ContainerTest');
  10. $fm->setProperty('username', 'php');
  11. $fm->setProperty('password', 'php');
  12.  
  13. // Search all records
  14. $command = $fm->newFindAllCommand('ContainerTest');
  15. $result = $command->execute();
  16.  
  17. // Check for errors
  18. if (FileMaker::isError($result)) {
  19. die($result->getMessage());
  20. }
  21.  
  22. // Loop over the records
  23. foreach ($result->getRecords() as $record) {
  24.  
  25. // Get the url to the container field
  26. $url = urlencode($record->getField('container'));
  27.  
  28. // Get the title of the record
  29. $title = $record->getField('title');
  30.  
  31. // Show a link to the record
  32. echo('<a href="img.php?-url=' . $url . '">' . $title . '</a><br/>');
  33.  
  34. }
  35.  
  36. ?>

Let's go over the source code line by line:

  • line 4: this statement includes the FileMaker PHP API
  • line 7-11: these lines setup the connection to the FileMaker Server
  • line 14-15: we setup a find all command which returns all records in the database and execute it
  • line 18-20: if an error is encountered, we stop the script and show the error message
  • line 23: we loop over all found records
  • line 26: we get the url for the container field using the $record->getField() function. We urlencode the url to make it safe to be included in a query string. We save the result in a variable.
  • line 29: we store the title of the record in a variable so that we can use it later on.
  • line 32: we show a link to the record and link to the "img.php" script passing the url as a query string variable

2. Creating the script that displays the container data

Now that we have the index.php script, we will create the img.php script that downloads or shows the container data.

  1. <?php
  2.  
  3. // Include the FileMaker API
  4. require_once('FileMaker.php');
  5.  
  6. // Make a connection with the FileMaker server
  7. $fm = & new FileMaker();
  8. $fm->setProperty('hostspec', 'http://localhost');
  9. $fm->setProperty('database', 'ContainerTest');
  10. $fm->setProperty('username', 'php');
  11. $fm->setProperty('password', 'php');
  12.  
  13. // Check that we have an url in the query string
  14. if (isset($_GET['-url'])){
  15.  
  16. // Put the url in a variable
  17. $url = $_GET['-url'];
  18.  
  19. // Search for the extension of the file
  20. $url = substr($url, 0, strpos($url, "?"));
  21. $url = substr($url, strrpos($url, ".") + 1);
  22.  
  23. // Send the correct Content-Type header
  24. if($url == "jpg"){
  25. header('Content-type: image/jpeg');
  26. } else if($url == "gif"){
  27. header('Content-type: image/gif');
  28. } else{
  29. header('Content-type: application/octet-stream');
  30. }
  31.  
  32. // Show the contents of the container field
  33. echo $fm->getContainerData($_GET['-url']);
  34.  
  35. }
  36.  
  37. ?>

Let's go over the source code line by line:

  • line 4: this statement includes the FileMaker PHP API
  • line 7-11: these lines setup the connection to the FileMaker Server
  • line 14: we check that an url was given in the query string
  • line 17: we store the url in a variable
  • line 20-21: the file extension for the container field is determined (see later)
  • line 24-30: based on the extension in the url, we send the correct HTTP Content-Type header.
  • line 33: using the url from the query string, we display the contents of the container field using the $fm->getContainerData() function.

3. Setting the correct HTTP Content-Type

In the url returned from the $record->getField() function, FileMaker embeds the extension that determines the file type of the contents of the container field. FileMaker knows about the following extensions:

  • JPEG image:
    /fmi/xml/cnt/data.jpg?-db=ContainerTest&-lay=ContainerTest&-recid=2&-field=picture(1)
  • GIF image:
    /fmi/xml/cnt/data.gif?-db=ContainerTest&-lay=ContainerTest&-recid=2&-field=picture(1)
  • All the others:
    /fmi/xml/cnt/data.cnt?-db=ContainerTest&-lay=ContainerTest&-recid=2&-field=picture(1)

With the following PHP code, we can extract the extension from this url:

  1. $url = substr($url, 0, strpos($url, "?"));
  2. $url = substr($url, strrpos($url, ".") + 1);

Based on the extension, we can set the correct HTTP content type.

4. Files for this example

Download phpandcontainerdata.zip

One Response to “Accessing container fields with PHP”

  1. Hickam Says:

    I downloaded your example files and set them up on my server. They worked perfectly. Just what I wanted! So, I changed the file name, Account, Password, and field names (Five total edits) and tested it in Safari. I got the page with my database’s three test records displayed as links just as you see on your solution but when I click a link I get the Apache default page. Since I see the links, I know that my database file is set up correctly (even so, I double checked it) and at least one of my sample records is the same file type (.zip) All of this is done on the same computer, same php pages… Any ideas?

Leave a Reply

You must be logged in to post a comment.