title: How do I create a product with additional attributes in Magento via Soap/Java
body: <p>Good day!</p>
  
  <p>I would like to use the Magento’s SOAP API to manage the product catalog, attributes etc. I'm running following configuration:-</p>
  
  <ul>
  <li>Magento 1.6</li>
  <li>Soap API WS-I compliance</li>
  <li>Mac OSX Lion</li>
  <li>Mamp 2.0.5</li>
  </ul>
  
  <p>In case someone wants to create a new product, it is necessary to set a few properties of the product object. 
  Following code will demonstrate my approach to do this :</p>
  
  <pre><code>    public int createProduct(DatabaseProduct product) {
  
          ArrayOfString categories = new ArrayOfString();
                  categories.getComplexObjectArray().add(categoryID);
          createEntity.setCategoryIds(categories);
  
          CatalogProductCreateEntity createEntity = populateCreateOrUpdateEntity(product);
  
          CatalogProductCreateRequestParam param = new CatalogProductCreateRequestParam();
          param.setSessionId(sessionId);
          param.setSet(setId);
          param.setSku(product.getSku());
          param.setType("simple");
          param.setStore(storeId);
          param.setProductData(createEntity);
  
          CatalogProductCreateResponseParam response = service.catalogProductCreate(param);
          return response.getResult();
      }
  
      private CatalogProductCreateEntity populateCreateOrUpdateEntity(DatabaseProduct product) {
  
          CatalogProductCreateEntity createEntity = new CatalogProductCreateEntity();
          createEntity.setShortDescription(product.getDescription().substring(0, 20) + "...");
          createEntity.setDescription(product.getDescription());
          createEntity.setName(product.getName());
          createEntity.setPrice(String.valueOf(product.getPrice()));
          createEntity.setStatus("1"); //active
          createEntity.setVisibility("4"); //visible in search/catalog
          createEntity.setWeight("70"); //some value 
          createEntity.setTaxClassId("2"); //standard
  
              AssociativeArray attributes = new AssociativeArray();            
  
              AssociativeEntity attr1 = new AssociativeEntity();
              attr1.("attribute1_key";
              attr1.("attribute1_value");
              attributes.getComplexObjectArray().add(attr1);
  
              AssociativeEntity attr2 = new AssociativeEntity();
              attr2.("attribute2_key");
              attr2.("attribute2_value");
              attributes.getComplexObjectArray().add(attr2);
  
          createEntity.setAdditionalAttributes(attributes);
  
          return createEntity;
      }
  </code></pre>
  
  <p>I realized that I get an error written to the "<code>system.log</code>" of Magento.</p>
  
  <pre><code>2012-01-21T09:41:01+00:00 DEBUG (7): First parameter must either be an object or the name of an existing class/opt/website/magento/app/code/core/Mage/Catalog/Model/Product/Api/V2.php
  </code></pre>
  
  <p>I could localize the error in the "<code>V2.php</code>" file on line 265. 
  According to the php.net documentation the "<code>property_exists()</code>" method only can check for fields in objects. 
  As a matter of fact the "<code>$productData</code>" variable holds a property called "<code>additional_attributes</code>" which is of the type array. 
  Therefore the execution of this code will lead to an error.</p>
  
  <p>Moreover I don’t know to reproduce the object the structure of the "<code>$productData</code>" object through the use of Magento’s SOAP API V2.</p>
  
  <p>If I examine this code ("<code>foreach</code>" loop) in line 270, it indicates that there is an object ("<code>$productData</code>") holding an array ("<code>additional_attributes</code>") which again shall encapsulate a set of key/value pairs (if I am right)</p>
  
  <pre><code>253        protected function _prepareDataForSave ($product, $productData)
  254     {
  255         if (property_exists($productData, 'website_ids') &amp;&amp; is_array($productData-&gt;website_ids)) {
  256             $product-&gt;setWebsiteIds($productData-&gt;website_ids);
  257         }
  258 
  259         Mage::log("debug1");
  260         Mage::log(property_exists($productData, 'additional_attributes'));
  261         
  262         Mage::log($productData);
  263         
  264         if (property_exists($productData, 'additional_attributes')) {
  265             if (property_exists($productData-&gt;additional_attributes, 'single_data')) {
  266                 
  267                 Mage::log("---&gt; single");
  268                 Mage::log($productData-&gt;additional_attributes);
  269                 
  270                 foreach ($productData-&gt;additional_attributes-&gt;single_data as $_attribute) {
  271                     $_attrCode = $_attribute-&gt;key;
  272                     $productData-&gt;$_attrCode = $_attribute-&gt;value;
  273                 }
  274             }
  275             if (property_exists($productData-&gt;additional_attributes, 'multi_data')) {
  276                 
  277                 Mage::log("---&gt; multi");
  278                 Mage::log($productData-&gt;additional_attributes);
  279                 
  280                 foreach ($productData-&gt;additional_attributes-&gt;multi_data as $_attribute) {
  281                     $_attrCode = $_attribute-&gt;key;
  282                     $productData-&gt;$_attrCode = $_attribute-&gt;value;
  283                 }
  284             }   
  285                 
  286             Mage::log("debugXXX");
  287             unset($productData-&gt;additional_attributes);
  288         }
  289         
  290         Mage::log("debug2");
  291         
  292         foreach ($product-&gt;getTypeInstance(true)-&gt;getEditableAttributes($product) as $attribute) {
  293             $_attrCode = $attribute-&gt;getAttributeCode();
  294             if ($this-&gt;_isAllowedAttribute($attribute) &amp;&amp; (isset($productData-&gt;$_attrCode))) {
  295                 $product-&gt;setData(
  296         ... etc ...
  </code></pre>
  
  <p>This seems to be a bug. So here is my question.</p>
  
  <p>Am I going right to call this an programming issue which shall be posted in the bug base? 
  Is there a way to get over this issue? 
  Shall I rewrite parts of the php.code from above to satisfy my need to handle product information to create a product properly ?</p>
  
  <p>Thanks in advance</p>
  
  <pre><code>    $productData
      (
              [name] =&gt; testname
              [description] =&gt; testdescription
              [short_description] =&gt; shorttestdescription
              [weight] =&gt; 70
              [status] =&gt; 1
              [visibility] =&gt; 4
              [price] =&gt; 359.0
              [tax_class_id] =&gt; 2
              [additional_attributes] =&gt; Array
              (
                      [attribute1] =&gt; 999.0
                      [attribute2] =&gt; testcontent
              )
      )
  </code></pre>
  
  <p>the CatalogProductCreate-Call from the WSDL generated by SoapUI:</p>
  
  <pre><code>&lt;soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/" xmlns:urn="urn:Magento"&gt;
     &lt;soapenv:Header/&gt;
     &lt;soapenv:Body&gt;
        &lt;urn:catalogProductCreateRequestParam&gt;
           &lt;sessionId&gt;?&lt;/sessionId&gt;
           &lt;type&gt;?&lt;/type&gt;
           &lt;set&gt;?&lt;/set&gt;
           &lt;sku&gt;?&lt;/sku&gt;
           &lt;productData&gt;
              &lt;!--Optional:--&gt;
              &lt;categories&gt;
                 &lt;!--Zero or more repetitions:--&gt;
                 &lt;complexObjectArray&gt;?&lt;/complexObjectArray&gt;
              &lt;/categories&gt;
              &lt;!--Optional:--&gt;
              &lt;websites&gt;
                 &lt;!--Zero or more repetitions:--&gt;
                 &lt;complexObjectArray&gt;?&lt;/complexObjectArray&gt;
              &lt;/websites&gt;
              &lt;!--Optional:--&gt;
              &lt;name&gt;?&lt;/name&gt;
              &lt;!--Optional:--&gt;
              &lt;description&gt;?&lt;/description&gt;
              &lt;!--Optional:--&gt;
              &lt;short_description&gt;?&lt;/short_description&gt;
              &lt;!--Optional:--&gt;
              &lt;weight&gt;?&lt;/weight&gt;
              &lt;!--Optional:--&gt;
              &lt;status&gt;?&lt;/status&gt;
              &lt;!--Optional:--&gt;
              &lt;url_key&gt;?&lt;/url_key&gt;
              &lt;!--Optional:--&gt;
              &lt;url_path&gt;?&lt;/url_path&gt;
              &lt;!--Optional:--&gt;
              &lt;visibility&gt;?&lt;/visibility&gt;
              &lt;!--Optional:--&gt;
              &lt;category_ids&gt;
                 &lt;!--Zero or more repetitions:--&gt;
                 &lt;complexObjectArray&gt;?&lt;/complexObjectArray&gt;
              &lt;/category_ids&gt;
              &lt;!--Optional:--&gt;
              &lt;website_ids&gt;
                 &lt;!--Zero or more repetitions:--&gt;
                 &lt;complexObjectArray&gt;?&lt;/complexObjectArray&gt;
              &lt;/website_ids&gt;
              &lt;!--Optional:--&gt;
              &lt;has_options&gt;?&lt;/has_options&gt;
              &lt;!--Optional:--&gt;
              &lt;gift_message_available&gt;?&lt;/gift_message_available&gt;
              &lt;!--Optional:--&gt;
              &lt;price&gt;?&lt;/price&gt;
              &lt;!--Optional:--&gt;
              &lt;special_price&gt;?&lt;/special_price&gt;
              &lt;!--Optional:--&gt;
              &lt;special_from_date&gt;?&lt;/special_from_date&gt;
              &lt;!--Optional:--&gt;
              &lt;special_to_date&gt;?&lt;/special_to_date&gt;
              &lt;!--Optional:--&gt;
              &lt;tax_class_id&gt;?&lt;/tax_class_id&gt;
              &lt;!--Optional:--&gt;
              &lt;tier_price&gt;
                 &lt;!--Zero or more repetitions:--&gt;
                 &lt;complexObjectArray&gt;
                    &lt;!--Optional:--&gt;
                    &lt;customer_group_id&gt;?&lt;/customer_group_id&gt;
                    &lt;!--Optional:--&gt;
                    &lt;website&gt;?&lt;/website&gt;
                    &lt;!--Optional:--&gt;
                    &lt;qty&gt;?&lt;/qty&gt;
                    &lt;!--Optional:--&gt;
                    &lt;price&gt;?&lt;/price&gt;
                 &lt;/complexObjectArray&gt;
              &lt;/tier_price&gt;
              &lt;!--Optional:--&gt;
              &lt;meta_title&gt;?&lt;/meta_title&gt;
              &lt;!--Optional:--&gt;
              &lt;meta_keyword&gt;?&lt;/meta_keyword&gt;
              &lt;!--Optional:--&gt;
              &lt;meta_description&gt;?&lt;/meta_description&gt;
              &lt;!--Optional:--&gt;
              &lt;custom_design&gt;?&lt;/custom_design&gt;
              &lt;!--Optional:--&gt;
              &lt;custom_layout_update&gt;?&lt;/custom_layout_update&gt;
              &lt;!--Optional:--&gt;
              &lt;options_container&gt;?&lt;/options_container&gt;
              &lt;!--Optional:--&gt;
              &lt;additional_attributes&gt;
                 &lt;!--Zero or more repetitions:--&gt;
                 &lt;complexObjectArray&gt;
                    &lt;key&gt;?&lt;/key&gt;
                    &lt;value&gt;?&lt;/value&gt;
                 &lt;/complexObjectArray&gt;
              &lt;/additional_attributes&gt;
              &lt;!--Optional:--&gt;
              &lt;stock_data&gt;
                 &lt;!--Optional:--&gt;
                 &lt;qty&gt;?&lt;/qty&gt;
                 &lt;!--Optional:--&gt;
                 &lt;is_in_stock&gt;?&lt;/is_in_stock&gt;
                 &lt;!--Optional:--&gt;
                 &lt;manage_stock&gt;?&lt;/manage_stock&gt;
                 &lt;!--Optional:--&gt;
                 &lt;use_config_manage_stock&gt;?&lt;/use_config_manage_stock&gt;
                 &lt;!--Optional:--&gt;
                 &lt;min_qty&gt;?&lt;/min_qty&gt;
                 &lt;!--Optional:--&gt;
                 &lt;use_config_min_qty&gt;?&lt;/use_config_min_qty&gt;
                 &lt;!--Optional:--&gt;
                 &lt;min_sale_qty&gt;?&lt;/min_sale_qty&gt;
                 &lt;!--Optional:--&gt;
                 &lt;use_config_min_sale_qty&gt;?&lt;/use_config_min_sale_qty&gt;
                 &lt;!--Optional:--&gt;
                 &lt;max_sale_qty&gt;?&lt;/max_sale_qty&gt;
                 &lt;!--Optional:--&gt;
                 &lt;use_config_max_sale_qty&gt;?&lt;/use_config_max_sale_qty&gt;
                 &lt;!--Optional:--&gt;
                 &lt;is_qty_decimal&gt;?&lt;/is_qty_decimal&gt;
                 &lt;!--Optional:--&gt;
                 &lt;backorders&gt;?&lt;/backorders&gt;
                 &lt;!--Optional:--&gt;
                 &lt;use_config_backorders&gt;?&lt;/use_config_backorders&gt;
                 &lt;!--Optional:--&gt;
                 &lt;notify_stock_qty&gt;?&lt;/notify_stock_qty&gt;
                 &lt;!--Optional:--&gt;
                 &lt;use_config_notify_stock_qty&gt;?&lt;/use_config_notify_stock_qty&gt;
              &lt;/stock_data&gt;
           &lt;/productData&gt;
           &lt;!--Optional:--&gt;
           &lt;store&gt;?&lt;/store&gt;
        &lt;/urn:catalogProductCreateRequestParam&gt;
     &lt;/soapenv:Body&gt;
  &lt;/soapenv:Envelope&gt;
  </code></pre>