github.com/hasnat/dolt/go@v0.0.0-20210628190320-9eb5d843fbb7/libraries/doltcore/sqle/dtables/log_table.go (about)

     1  // Copyright 2019 Dolthub, Inc.
     2  //
     3  // Licensed under the Apache License, Version 2.0 (the "License");
     4  // you may not use this file except in compliance with the License.
     5  // You may obtain a copy of the License at
     6  //
     7  //     http://www.apache.org/licenses/LICENSE-2.0
     8  //
     9  // Unless required by applicable law or agreed to in writing, software
    10  // distributed under the License is distributed on an "AS IS" BASIS,
    11  // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    12  // See the License for the specific language governing permissions and
    13  // limitations under the License.
    14  
    15  package dtables
    16  
    17  import (
    18  	"io"
    19  
    20  	"github.com/dolthub/go-mysql-server/sql"
    21  
    22  	"github.com/dolthub/dolt/go/libraries/doltcore/doltdb"
    23  	"github.com/dolthub/dolt/go/libraries/doltcore/env/actions"
    24  	"github.com/dolthub/dolt/go/libraries/doltcore/sqle/sqlutil"
    25  	"github.com/dolthub/dolt/go/store/types"
    26  )
    27  
    28  var _ sql.Table = (*LogTable)(nil)
    29  
    30  // LogTable is a sql.Table implementation that implements a system table which shows the dolt commit log
    31  type LogTable struct {
    32  	ddb  *doltdb.DoltDB
    33  	head *doltdb.Commit
    34  }
    35  
    36  // NewLogTable creates a LogTable
    37  func NewLogTable(_ *sql.Context, ddb *doltdb.DoltDB, head *doltdb.Commit) sql.Table {
    38  	return &LogTable{ddb: ddb, head: head}
    39  }
    40  
    41  // Name is a sql.Table interface function which returns the name of the table which is defined by the constant
    42  // LogTableName
    43  func (dt *LogTable) Name() string {
    44  	return doltdb.LogTableName
    45  }
    46  
    47  // String is a sql.Table interface function which returns the name of the table which is defined by the constant
    48  // LogTableName
    49  func (dt *LogTable) String() string {
    50  	return doltdb.LogTableName
    51  }
    52  
    53  // Schema is a sql.Table interface function that gets the sql.Schema of the log system table.
    54  func (dt *LogTable) Schema() sql.Schema {
    55  	return []*sql.Column{
    56  		{Name: "commit_hash", Type: sql.Text, Source: doltdb.LogTableName, PrimaryKey: true},
    57  		{Name: "committer", Type: sql.Text, Source: doltdb.LogTableName, PrimaryKey: false},
    58  		{Name: "email", Type: sql.Text, Source: doltdb.LogTableName, PrimaryKey: false},
    59  		{Name: "date", Type: sql.Datetime, Source: doltdb.LogTableName, PrimaryKey: false},
    60  		{Name: "message", Type: sql.Text, Source: doltdb.LogTableName, PrimaryKey: false},
    61  	}
    62  }
    63  
    64  // Partitions is a sql.Table interface function that returns a partition of the data.  Currently the data is unpartitioned.
    65  func (dt *LogTable) Partitions(*sql.Context) (sql.PartitionIter, error) {
    66  	return sqlutil.NewSinglePartitionIter(types.Map{}), nil
    67  }
    68  
    69  // PartitionRows is a sql.Table interface function that gets a row iterator for a partition
    70  func (dt *LogTable) PartitionRows(sqlCtx *sql.Context, _ sql.Partition) (sql.RowIter, error) {
    71  	return NewLogItr(sqlCtx, dt.ddb, dt.head)
    72  }
    73  
    74  // LogItr is a sql.RowItr implementation which iterates over each commit as if it's a row in the table.
    75  type LogItr struct {
    76  	commits []*doltdb.Commit
    77  	idx     int
    78  }
    79  
    80  // NewLogItr creates a LogItr from the current environment.
    81  func NewLogItr(sqlCtx *sql.Context, ddb *doltdb.DoltDB, head *doltdb.Commit) (*LogItr, error) {
    82  	commits, err := actions.TimeSortedCommits(sqlCtx, ddb, head, -1)
    83  
    84  	if err != nil {
    85  		return nil, err
    86  	}
    87  
    88  	return &LogItr{commits, 0}, nil
    89  }
    90  
    91  // Next retrieves the next row. It will return io.EOF if it's the last row.
    92  // After retrieving the last row, Close will be automatically closed.
    93  func (itr *LogItr) Next() (sql.Row, error) {
    94  	if itr.idx >= len(itr.commits) {
    95  		return nil, io.EOF
    96  	}
    97  
    98  	defer func() {
    99  		itr.idx++
   100  	}()
   101  
   102  	cm := itr.commits[itr.idx]
   103  	meta, err := cm.GetCommitMeta()
   104  
   105  	if err != nil {
   106  		return nil, err
   107  	}
   108  
   109  	h, err := cm.HashOf()
   110  
   111  	if err != nil {
   112  		return nil, err
   113  	}
   114  
   115  	return sql.NewRow(h.String(), meta.Name, meta.Email, meta.Time(), meta.Description), nil
   116  }
   117  
   118  // Close closes the iterator.
   119  func (itr *LogItr) Close(*sql.Context) error {
   120  	return nil
   121  }