2026_08_24_140000_create_agent_system_tables.php 9.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201
  1. <?php
  2. use Illuminate\Database\Migrations\Migration;
  3. use Illuminate\Database\Schema\Blueprint;
  4. use Illuminate\Support\Facades\Schema;
  5. return new class extends Migration {
  6. public function up(): void
  7. {
  8. if (!Schema::hasTable('agents')) {
  9. Schema::create('agents', function (Blueprint $table) {
  10. $table->id();
  11. $table->unsignedBigInteger('parent_id')->nullable()->index();
  12. $table->string('path', 512)->default('/')->index();
  13. $table->unsignedTinyInteger('level')->default(1);
  14. $table->string('username', 64)->unique();
  15. $table->string('password');
  16. $table->string('withdraw_password')->default('');
  17. $table->string('real_name', 128)->default('');
  18. $table->string('invitation_code', 32)->unique();
  19. $table->decimal('balance', 18, 4)->default(0);
  20. $table->decimal('frozen_balance', 18, 4)->default(0);
  21. $table->decimal('deposit_fee_rate', 8, 4)->default(0);
  22. $table->decimal('withdraw_fee_rate', 8, 4)->default(0);
  23. $table->decimal('profit_commission_rate', 8, 4)->default(0);
  24. $table->unsignedTinyInteger('status')->default(1)->index();
  25. $table->timestamp('last_login_at')->nullable();
  26. $table->string('last_login_ip', 64)->default('');
  27. $table->unsignedBigInteger('created_by')->nullable();
  28. $table->timestamps();
  29. $table->index(['level', 'status']);
  30. });
  31. }
  32. if (!Schema::hasTable('agent_tokens')) {
  33. Schema::create('agent_tokens', function (Blueprint $table) {
  34. $table->id();
  35. $table->unsignedBigInteger('agent_id')->unique();
  36. $table->char('token_hash', 64)->unique();
  37. $table->timestamp('expires_at')->index();
  38. $table->timestamp('last_used_at')->nullable();
  39. $table->string('ip', 64)->default('');
  40. $table->string('device', 16)->default('');
  41. $table->timestamps();
  42. });
  43. }
  44. if (!Schema::hasTable('agent_domains')) {
  45. Schema::create('agent_domains', function (Blueprint $table) {
  46. $table->id();
  47. $table->unsignedBigInteger('agent_id')->index();
  48. $table->string('type', 16)->comment('pc/h5')->index();
  49. $table->string('domain', 255)->index();
  50. $table->string('host', 255)->index();
  51. $table->unsignedTinyInteger('status')->default(1);
  52. $table->timestamps();
  53. $table->unique(['agent_id', 'type'], 'uniq_agent_domain_type');
  54. });
  55. }
  56. if (!Schema::hasTable('agent_login_logs')) {
  57. Schema::create('agent_login_logs', function (Blueprint $table) {
  58. $table->id();
  59. $table->unsignedBigInteger('agent_id')->index();
  60. $table->string('username', 64);
  61. $table->string('domain', 255)->default('');
  62. $table->string('ip', 64)->default('')->index();
  63. $table->string('country', 128)->default('');
  64. $table->string('region', 128)->default('');
  65. $table->string('city', 128)->default('');
  66. $table->string('device', 16)->default('')->index();
  67. $table->string('user_agent', 512)->default('');
  68. $table->timestamp('login_at')->index();
  69. $table->timestamps();
  70. });
  71. }
  72. if (!Schema::hasTable('agent_balance_logs')) {
  73. Schema::create('agent_balance_logs', function (Blueprint $table) {
  74. $table->id();
  75. $table->unsignedBigInteger('agent_id')->index();
  76. $table->string('type', 32)->index();
  77. $table->decimal('amount', 18, 4);
  78. $table->decimal('before_balance', 18, 4);
  79. $table->decimal('after_balance', 18, 4);
  80. $table->string('reference_type', 64)->default('');
  81. $table->unsignedBigInteger('reference_id')->nullable();
  82. $table->string('operator_type', 16)->default('system');
  83. $table->unsignedBigInteger('operator_id')->nullable();
  84. $table->string('idempotency_key', 96)->unique();
  85. $table->string('remark', 500)->default('');
  86. $table->timestamps();
  87. $table->index(['agent_id', 'created_at']);
  88. });
  89. }
  90. if (!Schema::hasTable('agent_withdraw_accounts')) {
  91. Schema::create('agent_withdraw_accounts', function (Blueprint $table) {
  92. $table->id();
  93. $table->unsignedBigInteger('agent_id')->index();
  94. $table->string('type', 32)->index();
  95. $table->string('name', 128)->default('');
  96. $table->string('account', 255);
  97. $table->string('bank_name', 128)->default('');
  98. $table->string('network', 32)->default('');
  99. $table->json('details')->nullable();
  100. $table->unsignedTinyInteger('status')->default(1);
  101. $table->timestamps();
  102. });
  103. }
  104. if (!Schema::hasTable('agent_withdrawals')) {
  105. Schema::create('agent_withdrawals', function (Blueprint $table) {
  106. $table->id();
  107. $table->string('order_no', 40)->unique();
  108. $table->string('request_key', 96)->unique();
  109. $table->unsignedBigInteger('agent_id')->index();
  110. $table->unsignedBigInteger('account_id')->nullable();
  111. $table->string('account_type', 32)->default('');
  112. $table->text('account_snapshot');
  113. $table->decimal('amount', 18, 4);
  114. $table->decimal('fee', 18, 4)->default(0);
  115. $table->decimal('actual_amount', 18, 4);
  116. $table->string('status', 24)->default('pending')->index();
  117. $table->string('remark', 500)->default('');
  118. $table->string('audit_remark', 500)->default('');
  119. $table->unsignedBigInteger('audit_admin_id')->nullable();
  120. $table->timestamp('audited_at')->nullable();
  121. $table->timestamp('paid_at')->nullable();
  122. $table->timestamps();
  123. $table->index(['agent_id', 'created_at']);
  124. });
  125. }
  126. if (!Schema::hasTable('agent_commissions')) {
  127. Schema::create('agent_commissions', function (Blueprint $table) {
  128. $table->id();
  129. $table->date('settlement_date');
  130. $table->unsignedBigInteger('agent_id')->index();
  131. $table->string('type', 16)->comment('flow/profit');
  132. $table->decimal('base_amount', 18, 4)->default(0);
  133. $table->decimal('rate', 8, 4)->default(0);
  134. $table->decimal('amount', 18, 4)->default(0);
  135. $table->unsignedBigInteger('bet_count')->default(0);
  136. $table->string('status', 16)->default('pending')->index();
  137. $table->json('snapshot')->nullable();
  138. $table->timestamp('credited_at')->nullable();
  139. $table->timestamps();
  140. $table->unique(['settlement_date', 'agent_id', 'type'], 'uniq_agent_commission_daily');
  141. });
  142. }
  143. if (!Schema::hasTable('agent_daily_stats')) {
  144. Schema::create('agent_daily_stats', function (Blueprint $table) {
  145. $table->id();
  146. $table->date('stat_date');
  147. $table->unsignedBigInteger('agent_id')->index();
  148. $table->unsignedInteger('direct_agents')->default(0);
  149. $table->unsignedInteger('direct_members')->default(0);
  150. $table->decimal('member_balance', 18, 4)->default(0);
  151. $table->decimal('deposit_amount', 18, 4)->default(0);
  152. $table->decimal('withdraw_amount', 18, 4)->default(0);
  153. $table->decimal('manual_credit', 18, 4)->default(0);
  154. $table->decimal('manual_debit', 18, 4)->default(0);
  155. $table->decimal('bonus_amount', 18, 4)->default(0);
  156. $table->decimal('rebate_amount', 18, 4)->default(0);
  157. $table->decimal('bet_amount', 18, 4)->default(0);
  158. $table->decimal('valid_bet_amount', 18, 4)->default(0);
  159. $table->unsignedBigInteger('bet_count')->default(0);
  160. $table->decimal('win_loss', 18, 4)->default(0);
  161. $table->decimal('commission_amount', 18, 4)->default(0);
  162. $table->decimal('company_profit', 18, 4)->default(0);
  163. $table->timestamps();
  164. $table->unique(['stat_date', 'agent_id'], 'uniq_agent_daily_stat');
  165. });
  166. }
  167. if (Schema::hasTable('users') && !Schema::hasColumn('users', 'agent_id')) {
  168. Schema::table('users', function (Blueprint $table) {
  169. $table->unsignedBigInteger('agent_id')->nullable()->index();
  170. });
  171. }
  172. }
  173. public function down(): void
  174. {
  175. if (Schema::hasTable('users') && Schema::hasColumn('users', 'agent_id')) {
  176. Schema::table('users', function (Blueprint $table) {
  177. $table->dropColumn('agent_id');
  178. });
  179. }
  180. foreach ([
  181. 'agent_daily_stats', 'agent_commissions',
  182. 'agent_withdrawals', 'agent_withdraw_accounts', 'agent_balance_logs',
  183. 'agent_login_logs', 'agent_domains', 'agent_tokens', 'agents',
  184. ] as $table) {
  185. Schema::dropIfExists($table);
  186. }
  187. }
  188. };