whole_func_string: function extend(o, p, deep) {
          // If `o` or `p` are not set bail
          if (!o || !p) {
              return o;
          }
  
          // Merge all props from `p` to `o`
          Object.keys(p).forEach(function (prop) { // For all props in p.
              // If property is present on target (o) and is not writable, skip iteration
              var propDescription = Object.getOwnPropertyDescriptor(o, prop);
              if (propDescription &&
                  !(isset(propDescription.get) && isset(propDescription.set)) &&
                  !propDescription.writable) {
                  return;
              }
              if (deep === true) {
                  if (isObject(p[prop]) && isObject(o[prop]) && !isEmptyObj(p[prop])) {
                      extend(o[prop], p[prop], deep);
                  }
                  else {
                      o[prop] = p[prop];
                  }
              }
              else {
                  o[prop] = p[prop];
              }
          });
  
          return o;
      }
func_code_string: function extend(o, p, deep) {
          // If `o` or `p` are not set bail
          if (!o || !p) {
              return o;
          }
  
          // Merge all props from `p` to `o`
          Object.keys(p).forEach(function (prop) { // For all props in p.
              // If property is present on target (o) and is not writable, skip iteration
              var propDescription = Object.getOwnPropertyDescriptor(o, prop);
              if (propDescription &&
                  !(isset(propDescription.get) && isset(propDescription.set)) &&
                  !propDescription.writable) {
                  return;
              }
              if (deep === true) {
                  if (isObject(p[prop]) && isObject(o[prop]) && !isEmptyObj(p[prop])) {
                      extend(o[prop], p[prop], deep);
                  }
                  else {
                      o[prop] = p[prop];
                  }
              }
              else {
                  o[prop] = p[prop];
              }
          });
  
          return o;
      }
func_documentation_string: Copy the enumerable properties of p to o, and return o.
  If o and p have a property by the same name, o's property is overwritten.
  @param o {*} - *object to extend
  @param p {*} - *object to extend from
  @param deep [Boolean=false] - Whether or not to do a deep extend (run extend on each prop if prop value is of type 'Object')
  @todo rename these variables to be more readable.
  @returns {*} - returns o