我开始学习数据库是如何工作的,我总是将所有数据放在一个表中。我正在查看一个开源项目,我想创建一个接口,数据库结构太复杂,我无法理解。
我确信它有一个关系数据库结构(如果我已经正确学习)。这就是数据库结构的样子:
-- Table structure for table `databasechangelog`
--
CREATE TABLE IF NOT EXISTS `databasechangelog` (
`ID` varchar(255) NOT NULL,
`AUTHOR` varchar(255) NOT NULL,
`FILENAME` varchar(255) NOT NULL,
`DATEEXECUTED` datetime NOT NULL,
`ORDEREXECUTED` int(11) NOT NULL,
`EXECTYPE` varchar(10) NOT NULL,
`MD5SUM` varchar(35) DEFAULT NULL,
`DESCRIPTION` varchar(255) DEFAULT NULL,
`COMMENTS` varchar(255) DEFAULT NULL,
`TAG` varchar(255) DEFAULT NULL,
`LIQUIBASE` varchar(20) DEFAULT NULL,
`CONTEXTS` varchar(255) DEFAULT NULL,
`LABELS` varchar(255) DEFAULT NULL
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
-- --------------------------------------------------------
-- Table structure for table `databasechangeloglock`
--
CREATE TABLE IF NOT EXISTS `databasechangeloglock` (
`ID` int(11) NOT NULL,
`LOCKED` bit(1) NOT NULL,
`LOCKGRANTED` datetime DEFAULT NULL,
`LOCKEDBY` varchar(255) DEFAULT NULL,
PRIMARY KEY (`ID`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
-- --------------------------------------------------------
-- Table structure for table `devices`
--
CREATE TABLE IF NOT EXISTS `devices` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(128) NOT NULL,
`uniqueid` varchar(128) NOT NULL,
`status` varchar(128) DEFAULT NULL,
`lastupdate` timestamp NULL DEFAULT NULL,
`positionid` int(11) DEFAULT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `uk_device_uniqueid` (`uniqueid`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1 AUTO_INCREMENT=2 ;
-- --------------------------------------------------------
-- Table structure for table `positions`
--
CREATE TABLE IF NOT EXISTS `positions` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`protocol` varchar(128) DEFAULT NULL,
`deviceid` int(11) NOT NULL,
`servertime` timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
`devicetime` timestamp NOT NULL DEFAULT '0000-00-00 00:00:00',
`fixtime` timestamp NOT NULL DEFAULT '0000-00-00 00:00:00',
`valid` bit(1) NOT NULL,
`latitude` double NOT NULL,
`longitude` double NOT NULL,
`altitude` float NOT NULL,
`speed` float NOT NULL,
`course` float NOT NULL,
`address` varchar(512) DEFAULT NULL,
`attributes` varchar(4096) NOT NULL,
PRIMARY KEY (`id`),
KEY `position_deviceid_fixtime` (`deviceid`,`fixtime`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1 AUTO_INCREMENT=145 ;
-- --------------------------------------------------------
-- Table structure for table `server`
--
CREATE TABLE IF NOT EXISTS `server` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`registration` bit(1) NOT NULL DEFAULT b'1',
`latitude` double NOT NULL DEFAULT '0',
`longitude` double NOT NULL DEFAULT '0',
`zoom` int(11) NOT NULL DEFAULT '0',
`map` varchar(128) DEFAULT NULL,
`language` varchar(128) DEFAULT NULL,
`distanceunit` varchar(128) DEFAULT NULL,
`speedunit` varchar(128) DEFAULT NULL,
`bingkey` varchar(128) DEFAULT NULL,
`mapurl` varchar(128) DEFAULT NULL,
`readonly` bit(1) NOT NULL DEFAULT b'0',
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1 AUTO_INCREMENT=2 ;
-- --------------------------------------------------------
-- Table structure for table `users`
--
CREATE TABLE IF NOT EXISTS `users` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(128) NOT NULL,
`email` varchar(128) NOT NULL,
`hashedpassword` varchar(128) NOT NULL,
`salt` varchar(128) NOT NULL,
`readonly` bit(1) NOT NULL DEFAULT b'0',
`admin` bit(1) NOT NULL DEFAULT b'0',
`map` varchar(128) NOT NULL DEFAULT 'osm',
`language` varchar(128) NOT NULL DEFAULT 'en',
`distanceunit` varchar(128) NOT NULL DEFAULT 'km',
`speedunit` varchar(128) NOT NULL DEFAULT 'kmh',
`latitude` double NOT NULL DEFAULT '0',
`longitude` double NOT NULL DEFAULT '0',
`zoom` int(11) NOT NULL DEFAULT '0',
PRIMARY KEY (`id`),
UNIQUE KEY `uk_user_email` (`email`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1 AUTO_INCREMENT=3 ;
-- --------------------------------------------------------
-- Table structure for table `user_device`
--
CREATE TABLE IF NOT EXISTS `user_device` (
`userid` int(11) NOT NULL,
`deviceid` int(11) NOT NULL,
KEY `fk_user_device_deviceid` (`deviceid`),
KEY `user_device_user_id` (`userid`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
--
-- Constraints for dumped tables
--
--
-- Constraints for table `positions`
--
ALTER TABLE `positions`
ADD CONSTRAINT `fk_position_deviceid` FOREIGN KEY (`deviceid`) REFERENCES `devices` (`id`) ON DELETE CASCADE;
--
-- Constraints for table `user_device`
--
ALTER TABLE `user_device`
ADD CONSTRAINT `fk_user_device_deviceid` FOREIGN KEY (`deviceid`) REFERENCES `devices` (`id`) ON DELETE CASCADE,
ADD CONSTRAINT `fk_user_device_userid` FOREIGN KEY (`userid`) REFERENCES `users` (`id`) ON DELETE CASCADE;
当用户注册时,它会在“users”表中添加一个条目,并且用户会获得一个id。
然后,当用户添加设备时,user_device表如下所示:
设备表如下所示:
这是一款GPS跟踪软件,因此每个设备都会在“位置”表中发布它的位置,如下所示:
因此,如果用户登录,如何查询位置表并从该用户的所有设备获取所有信息?我假设我需要加入表格,但我不知道该怎么做。任何帮助将不胜感激。
答案 0 :(得分:2)
让我们逐步建立它。首先,您想要的实际数据是什么?
查询职位表
好的,从那开始:
SELECT
*
FROM
positions
现在您想如何进一步过滤该数据?
来自该用户的所有设备
好的,我们需要将此表(positions
)通过设备与用户联系起来。所以最终我们需要这样的WHERE
条款:
WHERE
userid = ?
但是positions
没有userid
,所以让我们一起来加入一些表,直到我们有一个表。 positions
有deviceid
,因此我们可以加入:
SELECT
*
FROM
positions
INNER JOIN devices
ON positions.deviceid = devices.id
但我们仍然没有userid
。 devices
本身并没有引用任何内容来进一步帮助我们。但是, 引用devices
,user_device
的表格。让我们加入:
SELECT
*
FROM
positions
INNER JOIN devices
ON positions.deviceid = devices.id
INNER JOIN user_device
ON devices.id = user_device.deviceid
您会发现我们现在获得了大量数据。但是,您还会看到我们现在正在获取userid
列,因此我们最终可以添加WHERE
子句:
SELECT
*
FROM
positions
INNER JOIN devices
ON positions.deviceid = devices.id
INNER JOIN user_device
ON devices.id = user_device.deviceid
WHERE
userid = ?
此时,我们应该从与positions
相关的任何device
中获取所有唯一user
。您可以通过将position
替换为SELECT *
来获取 SELECT positions.*
数据,或者您可以明确定义要从哪些表中选择哪些列。
答案 1 :(得分:0)
从您的笔记中可以看出,您知道用户何时登录他所拥有的设备。如果这是正确的,您不应该需要加入。只需在position.deviceid =登录设备的位置表上进行选择。