Create a proxy that handles data collecting better.

@param string $class
@param string &$proxyFile where we store the proxy class

@return string the name of a much much better class
506491
public function createProxy($class, &$proxyFile = null)
    {
        $proxyClass = $this->getProxyClass($class);
        $class      = '\\'.rtrim($class, '\\');
        $proxyFile  = $this->proxyDirectory.'/'.$proxyClass.'.php';

        if (class_exists($proxyClass)) {
            return $proxyClass;
        }

        if (file_exists($proxyFile)) {
            require $proxyFile;

            return $proxyClass;
        }

        $content = file_get_contents(dirname(__DIR__).'/Resources/proxy/template.php');
        $content = str_replace('__TPL_CLASS__', $proxyClass, $content);
        $content = str_replace('__TPL_EXTENDS__', $class, $content);

        $this->checkProxyDirectory();
        file_put_contents($proxyFile, $content);
        require $proxyFile;

        return $proxyClass;
    }
719023
public function loadClass(string $class)
    {
        if (strpos($class, 'Proxy\__Transactional__\\') !== 0) {
            return null;
        }

        if ($file = $this->findProxyFile($class)) {
            require_once $file;

            return true;
        }

        return null;
    }
79300
public function getProxyClassName($className)
    {
        $suffix = ltrim($className, '\\');
        
        if ($this->proxyClassSuffix !== null) {
            $suffix .= $this->proxyClassSuffix;    
        }
        
        return rtrim($this->proxyNamespace, '\\') . '\\'.self::MARKER.'\\' . $suffix;
    }
400776
public function getManagerForClass($class)
    {
        // Check for namespace alias
        if (strpos($class, ':') !== false) {
            list($namespaceAlias, $simpleClassName) = explode(':', $class, 2);
            $class                                  = $this->getAliasNamespace($namespaceAlias) . '\\' . $simpleClassName;
        }

        $proxyClass = new ReflectionClass($class);
        if ($proxyClass->implementsInterface(Proxy::class)) {
            $class = $proxyClass->getParentClass()->getName();
        }

        $managerNames = $this->getManagerNames();

        if (count($managerNames) === 1) {
            return $this->getManager(reset($managerNames));
        }

        foreach ($managerNames as $name) {
            $manager = $this->getManager($name);

            if (!$manager->getMetadataFactory()->isTransient($class)) {
                foreach ($manager->getMetadataFactory()->getAllMetadata() as $metadata) {
                    if ($metadata->getName() === $class) {
                        return $manager;
                    }
                }
            }
        }
    }
361473
def use(proxy, options = {}, &block)
      proxy = Moneta.const_get(proxy) if Symbol === proxy
      raise ArgumentError, 'You must give a Class or a Symbol' unless Class === proxy
      @proxies.unshift [proxy, options, block]
      nil
    end
214960
public function findFile($class)
    {
        if (false === $file = apc_fetch($this->prefix.$class)) {
            apc_store($this->prefix.$class, $file = $this->decorated->findFile($class));
        }

        return $file;
    }
1178657
public function make($class)
    {
        $controller = $this->container->make($class);
        $controller->setServer($this->makeServer());
        $controller->setView($this->makeView());
        $controller->setSession($this->makeSession());
        $controller->setUrlGenerator($this->makeUrlGenerator());

        return $controller;
    }
1074593
public function batchDelete($class, ProxyQueryInterface $queryProxy)
    {
        $objects = $this->getBatchObjects($class, $queryProxy);
        foreach ($objects as $object) {
            $this->delete($object);
        }
    }
282574
public static function create($class)
    {
        try {
            $reflection = new \ReflectionClass($class);
        } catch (\ReflectionException $e) {
            return false;
        }

        $constructor = $reflection->getConstructor();

        // If there are no parameters, just return a new object.
        if (null === $constructor) {
            return new $class;
        }

        $newInstanceArgs = self::getMethodArgs($constructor);

        // Create a callable for the dataStorage
        return $reflection->newInstanceArgs($newInstanceArgs);
    }
165754
@SuppressWarnings("unchecked")
    public Class<? extends T> defineClass() {
        if (generatedClass == null) {
            synchronized (this) {
                if (generatedClass == null) {
                    try {
                        // first check that the proxy has not already been created
                        generatedClass = (Class<? extends T>) classLoader.loadClass(this.className);
                    } catch (ClassNotFoundException e) {
                        buildClassDefinition();
                        if (protectionDomain == null) {
                            generatedClass = (Class<? extends T>) classFile.define();
                        } else {
                            generatedClass = (Class<? extends T>) classFile.define(protectionDomain);
                        }
                        afterClassLoad(generatedClass);
                    }
                    classFile = null;
                }
            }
        }
        return generatedClass;
    }
1023670
public synchronized Class getProxyClass()
    {
        if ((proxyClass == null) && (proxyClassName != null))
        {
            if (isDynamicProxy())
            {
                /**
                 * AClute: Return the same class back if it is dynamic. This signifies
                 * that this class become the base to a generated sub-class, regadless
                 * of which Proxy implementation is used
                 */
                return getClassOfObject();
            }
            else
            {
                try
                {
                    proxyClass = ClassHelper.getClass(proxyClassName);
                }
                catch (ClassNotFoundException e)
                {
                    throw new MetadataException(e);
                }
            }
        }
        return proxyClass;
    }
213947
private static function forkTrait(\ReflectionClass $class): \ReflectionClass
    {
        $code = sprintf(
                "abstract class %sCallMapFork {\n"
                . "    use \%s;\n}",
                $class->getShortName(),
                $class->getName()
        );
        if ($class->inNamespace()) {
            $code = sprintf(
                    "namespace %s {\n%s}\n",
                    $class->getNamespaceName(),
                    $code
            );
        }

        try {
            $compile = self::$compile;
            $compile($code);
        } catch (\ParseError $pe) {
            throw new ProxyCreationFailure(
                    'Failure while creating forked trait instance of '
                    . $class->getName() . ': ' . $pe->getMessage(),
                    $pe
            );
        }

        return new \ReflectionClass($class->getName() . 'CallMapFork');
    }
915064
protected function getRid(Proxy $proxy)
    {
        $metadata = $this->getManager()->getClassMetadata(get_parent_class($proxy));

        return $metadata->getIdentifierValues($proxy);
    }
234582
private function generateProxyClass(): string
    {
        $class = $this->reflectionClass;

        if ($class->isFinal()) {
            throw new \RuntimeException(sprintf(
                'Can not generate proxy for final class "%s".',
                $class->getName()
            ));
        }

        if ($class->isAbstract()) {
            throw new \RuntimeException(sprintf(
                'Can not generate proxy for abstract class "%s".',
                $class->getName()
            ));
        }

        $methodCodes = [];

        $uses = $this->getAllUseStatementsMarkedAsAnnotation($class);
        $uses[] = 'FiveLab\Component\Transactional\Proxy\ProxyInterface as FiveLabTransactionalProxyInterface';

        $uses = \array_map(function ($use) {
            return 'use '.$use.';';
        }, $uses);

        $interfaces = [
            'FiveLabTransactionalProxyInterface',
        ];

        foreach ($this->getProxyMethods() as $method) {
            $methodCodes[] = $this->generateProxyMethod($method);
        }

        $docComment = $class->getDocComment();

        $templateVariables = [
            'uses'           => \implode("\n", $uses),
            'namespace'      => $class->getNamespaceName(),
            'docComment'     => $docComment,
            'proxyClassName' => $class->getShortName().'Proxy',
            'className'      => '\\'.$class->getName(),
            'proxyMethods'   => \implode("\n\n", $methodCodes),
            'interfaces'     => \implode(', ', $interfaces),
            'realClassName'  => $class->getName(),
        ];

        $template = $this->getTemplateForProxyClass();
        $code = $this->replaceVariables($template, $templateVariables);

        $lines = \explode("\n", $code);
        $lines = \array_map('rtrim', $lines);

        return \implode("\n", $lines);
    }
232446
public function refreshDocumentForProxy($className, Proxy $document)
    {
        $node = $this->session->getNode($this->determineDocumentId($document));

        $hints = ['refresh' => true, 'fallback' => true];

        $oid = spl_object_hash($document);
        if (isset($this->documentLocales[$oid]['current'])) {
            $hints['locale'] = $this->documentLocales[$oid]['current'];
        }

        $this->getOrCreateDocument($className, $node, $hints);
    }
427440
protected function getProxyClassDirAndCreate($namespace)
    {
        $path = str_replace("\\", DIRECTORY_SEPARATOR, $namespace);
        $dir = $this->config->getProxyRootDir() . DIRECTORY_SEPARATOR . $path;
        if (!Util::createDirIfNotExists($dir)) {
            throw new InitiallyRpcException("Proxy builder error: get proxy class dir and create it");
        }

        return $dir;
    }
966729
@Override
    public Class<?> getProxyClass() {
        if (proxyClass != null) {
            return proxyClass;
        }
        try {
            if (StringUtils.isNotBlank(interfaceId)) {
                this.proxyClass = ClassUtils.forName(interfaceId);
                if (!proxyClass.isInterface()) {
                    throw ExceptionUtils.buildRuntime("service.interfaceId",
                        interfaceId, "interfaceId must set interface class, not implement class");
                }
            } else {
                throw ExceptionUtils.buildRuntime("service.interfaceId",
                    "null", "interfaceId must be not null");
            }
        } catch (SofaRpcRuntimeException e) {
            throw e;
        } catch (Throwable e) {
            throw new SofaRpcRuntimeException(e.getMessage(), e);
        }
        return proxyClass;
    }